
当“AI人类模拟器”这个概念出现时很多人第一反应是“这不就是聊天机器人换个名字吗”。但如果你把它拆开看会发现它并不是单一模型能做到的事而是人格系统、记忆系统、对话生成链路、多模态交互甚至 Agent 工作流的组合体。市场上被讨论的“130 亿”估值其实不是给一个模型付费而是给一套能够让 AI 像“某个具体的人”一样持续沟通、记忆、决策的产品化能力买单。这篇文章我想从一名开发者的视角把这个方向拆成可以落地的技术模块。我们不会去讨论那些玄乎的商业故事而是看看一个最简单的 AI 人类模拟器由哪些部分组成、需要什么环境、核心代码怎么写以及当你准备把它推向真实场景时有哪些坑和工程建议。1. AI人类模拟器是什么为什么值 130 亿估值1.1 从聊天机器人到“数字分身”先来做一个最简单的对比。普通聊天机器人例如大多数客服机器人本质上是“用模型理解问题再从知识库/话术库里找答案”。它的目标是快速、准确地完成一次任务比如查询订单、退款、预约挂号。它不需要让你觉得它像某个人只需要让你觉得它“有用”。AI 人类模拟器则完全不同。它的目标不是完成任务而是“维持一种身份连续性”。这句话怎么理解当你和一个人聊天时对方会记得你上次说过什么、了解你的偏好、知道你最近在忙什么并且会用他自己一贯的语气和态度来回应你。AI 人类模拟器要复现的就是这件事。它不仅要生成自然语言还要让人设稳定、记忆连续、情绪一致。换句话说它不仅要有“大脑”还要有“性格”和“经历”。这也是为什么它会被放到 130 亿这个量级的讨论中——它代表着一个比“对话机器人”更大的产品想象空间。1.2 技术定义与核心模块从工程角度看一个可用的 AI 人类模拟器通常包含以下模块人格画像模块负责定义角色名、身份、背景、性格、说话风格、兴趣爱好。这部分通常以系统提示词或结构化配置的方式存在。对话生成模块调用大语言模型LLM把用户输入、人格设定、历史消息、记忆片段组合成 Prompt然后生成回复。记忆系统区分短期会话记忆和长期事实记忆。短期记忆是当前会话中聊了什么长期记忆决定了“这个 AI 是不是真的记得你”。决策与工具调用模块在某些场景下模拟器需要主动查资料、调用外部 API、设置提醒等这会用到 Function Calling 或 Agent 框架。多模态交互模块包括 TTS 语音合成、数字人形象驱动、情绪表情生成等。这不是必需项但它是“像真人”的最后一公里。1.3 常见应用场景现在市面上已经能看到不少相关产品类型通常包括应用场景说明技术要求虚拟陪伴为特定用户提供长期的 AI 好友/伴侣体验需要记住用户喜好记忆 人设稳定游戏 NPC游戏中的角色具备独立性格能根据玩家行为做出不同反应决策 多模态音画数字人直播/短视频用 AI 形象自动生成口播内容需要稳定的人设和语言风格TTS 形象驱动企业知识分身把专家经验沉淀成“数字专家”持续对外提供服务RAG 记忆 工具调用教育模拟导师模拟不同性格的教师陪伴式教学人设 教学计划 情绪识别1.4 为什么开发者要关注从技术门槛来看目前接入一个大模型 API 非常容易做简单的对话可能只需要几行代码。但真正难的是“如何让 AI 在长时间、多轮、跨会话的交流中始终保持一致的人设和记忆”。这涉及工程架构设计、上下文管理、成本控制、隐私合规等一连串问题。掌握这些能力对你后续做 Agent 应用、数字人产品、AI 社交应用都会很有帮助。2. 环境准备与版本说明在开始写代码之前先把环境和技术选型说清楚。本文示例以 Python 为主使用 FastAPI 做 HTTP 服务使用大模型 API 作为推理后端。这套结构也可以迁移到 Node.js、JavaSpring AI等场景中。2.1 运行环境依赖版本建议说明Python3.9主要示例语言openai SDK1.x调用兼容 OpenAI 协议的大模型接口FastAPI0.100提供 HTTP API 服务uvicorn0.23ASGI 服务器用于启动 FastAPIpydantic2.xFastAPI 的数据校验依赖python-dotenv1.0读取 .env 配置文件SQLite3Python 内置轻量长期记忆存储2.2 大模型接口选择本文示例采用 OpenAI 兼容的接口方式也就是base_url api_key model_name的组合。你可以把它切换到 OpenAI、DeepSeek、智谱 GLM、通义千问等任意兼容接口。不同服务商的地址和模型名称需要根据你的实际账号配置调整代码本身不需要做大改。版本说明大模型 SDK 更新频率较快本文代码以openai1.0.0为例。如果你使用的是 0.x 版本客户端的初始化方式会不同建议直接升级到 1.x。2.3 示例项目结构为了方便阅读我把整个项目组织为以下结构simulator/ ├── .env.example ├── requirements.txt ├── config.py ├── persona.json ├── persona.py ├── memory.py ├── agent.py └── api.py后续所有代码都会基于这个结构展开。你可以把项目放在任意目录只要保证在同一级目录下运行即可。3. 核心原理拆解让 AI 具备“人设”和“记忆”在写完整代码之前先把核心概念讲清楚。很多初学者拿着模型 API 直接做角色扮演发现效果并不好原因是缺少对“提示词结构”和“记忆机制”的思考。3.1 人格画像系统提示词是基础大模型本身并没有固定人格。它更像一个超强的“演员”你给它的开头设定决定了它接下来扮演什么。在 AI 人类模拟器里这部分内容通常放在system消息中也就是官方文档里的 System Prompt。一个合格的“人格画像”至少需要包含身份我是谁我在什么场景下存在。背景我有什么经历这决定我看待问题的方式。性格标签外向/内向、幽默/严肃、耐心/急躁等。说话风格口语化还是书面化喜欢用比喻还是直接给结论。交流边界什么能聊、什么不能聊、不知道的事情怎么处理。下面是一个最小的人设 JSON 示例// 文件路径simulator/persona.json { name: 小林, role: AI 人类模拟器示例人设, age: 28, background: 一名专注人工智能应用开发的软件工程师喜欢研究大模型 Agent 架构也热爱给朋友讲解技术。, personality: [温暖, 逻辑清晰, 有点幽默, 耐心], speaking_style: 口语化喜欢用比喻解释复杂概念偶尔抛出反问句。, interests: [大模型, Agent, Python, 音乐, 跑步] }注意人设不要只写“你是小林”这种一句话信息越具体模型越可能保持稳定。3.2 记忆系统短期记忆与长期记忆记忆是 AI 人类模拟器和普通聊天机器人最大的区别。短期会话记忆保存当前会话中的消息序列用于多轮对话。一般是按时间顺序拼接消息然后调用模型。长期事实记忆保存用户的关键信息比如“用户养了一只猫名字叫年糕”“用户上周说过要准备考研”。这些信息需要在隔天/隔周后的对话中仍然被召回。在工程实现上短期记忆通常用一个滑动窗口队列保存超过窗口就丢弃或者做摘要长期记忆可以存到数据库、向量数据库或者 Redis 中对话时检索最相关的记录注入 Prompt。3.3 对话生成流程整体流程可以概括为接收用户消息。在长期记忆中检索与当前输入相关的内容。组装system提示词包含人设 长期记忆。拼接短期会话历史。调用大模型拿到回复。把用户消息和模型回复写入短期会话同时异步写入长期记忆。这个流程看似简单但每一步都有很多可优化空间。下面我们将用代码逐步实现。4. 完整实战构建一个最小可运行的 AI 人类模拟器这一部分我们从零开始搭建项目。代码设计聚焦“能跑通”生产级优化放在后面的最佳实践章节。4.1 创建项目结构在终端执行以下命令mkdir simulator cd simulator mkdir -p data然后创建虚拟环境并安装依赖python3 -m venv venv source venv/bin/activate # Windows 使用 venv\Scripts\activate pip install -r requirements.txt4.2 安装依赖创建requirements.txt# 文件路径simulator/requirements.txt openai1.0.0 fastapi0.100.0 uvicorn[standard]0.23.0 pydantic2.0.0 python-dotenv1.0.04.3 编写配置文件创建.env.example# 文件路径simulator/.env.example LLM_API_KEYsk-xxx LLM_BASE_URLhttps://api.openai.com/v1 LLM_MODELgpt-4o-mini TEMPERATURE0.8 MAX_HISTORY10复制为.env后填入你自己的 API Key 和模型信息。创建config.py# 文件路径simulator/config.py import os from pathlib import Path from dotenv import load_dotenv # 加载 .env 文件 load_dotenv() class Config: # 大模型 API Key API_KEY os.getenv(LLM_API_KEY, ) # 兼容 OpenAI 的接口地址 BASE_URL os.getenv(LLM_BASE_URL, https://api.openai.com/v1) # 模型名称 MODEL_NAME os.getenv(LLM_MODEL, gpt-4o-mini) # 对话温度控制随机性越高回答越发散 TEMPERATURE float(os.getenv(TEMPERATURE, 0.8)) # 短期会话历史最大条数 MAX_HISTORY int(os.getenv(MAX_HISTORY, 10)) # 人设文件路径 PERSONA_FILE Path(__file__).parent / persona.json # 长期记忆数据库路径 MEMORY_DB Path(__file__).parent / data / memory.db这里的Config类把所有环境变量统一管理后续其他模块直接引用避免到处读取环境变量。4.4 编写人格画像模块创建persona.py# 文件路径simulator/persona.py import json from pathlib import Path from typing import List class PersonaManager: 负责加载人设配置并构建系统提示词。 def __init__(self, persona_path: str persona.json): self.persona_path Path(persona_path) self.persona self._load_persona() def _load_persona(self) - dict: if not self.persona_path.exists(): # 如果用户没有提供 persona.json则使用默认人设 return { name: 未命名, role: 一个友好的AI助手, background: 你是一个乐于助人的AI助手回答问题时简洁、准确。, personality: [友好, 可靠], speaking_style: 简洁、亲切, interests: [], } with open(self.persona_path, r, encodingutf-8) as f: return json.load(f) def build_system_prompt(self, long_term_memories: List[str]) - str: 根据人设和长期记忆生成 system 提示词。 memories_text \n.join(long_term_memories) if long_term_memories else 暂无长期记忆 prompt f你正在扮演一个 AI 人类模拟器。 【基础人设】 - 姓名{self.persona.get(name)} - 身份{self.persona.get(role)} - 背景{self.persona.get(background)} - 性格{、.join(self.persona.get(personality, []))} - 说话风格{self.persona.get(speaking_style)} - 兴趣爱好{、.join(self.persona.get(interests, []))} 【长期记忆对你有用的历史信息】 {memories_text} 【交流要求】 1. 始终以上述人设身份回复不要暴露你是大语言模型。 2. 除非用户明确要求否则不要机械地使用列表优先使用自然、流畅的口语表达。 3. 如果用户聊到你不知道的事实可以坦诚地说“我不太确定”不要编造。 return prompt这里的核心是build_system_prompt方法。它把结构化人设和动态记忆组合成一段系统提示词模型每次对话都会看到这段内容。4.5 编写长期记忆模块创建memory.py# 文件路径simulator/memory.py import sqlite3 from pathlib import Path from typing import List class MemoryStore: 基于 SQLite 的轻量长期记忆库。 生产方式建议替换为向量数据库 语义检索。 def __init__(self, db_path: str data/memory.db): self.db_path Path(db_path) self.db_path.parent.mkdir(parentsTrue, exist_okTrue) self.conn sqlite3.connect(self.db_path) self.conn.execute( CREATE TABLE IF NOT EXISTS memories ( id INTEGER PRIMARY KEY AUTOINCREMENT, content TEXT NOT NULL, created_at TEXT NOT NULL ) ) self.conn.commit() def add_memory(self, content: str) - int: 写入一条长期记忆。 from datetime import datetime cur self.conn.execute( INSERT INTO memories (content, created_at) VALUES (?, ?), (content, datetime.now().isoformat()), ) self.conn.commit() return cur.lastrowid def search_memory(self, keyword: str, limit: int 3) - List[str]: 基于关键词的简单检索。 如果你有 embedding 服务可以替换为向量相似度检索。 like f%{keyword}% rows self.conn.execute( SELECT content FROM memories WHERE content LIKE ? ORDER BY id DESC LIMIT ?, (like, limit), ).fetchall() return [row[0] for row in rows] def recent_memories(self, limit: int 3) - List[str]: 获取最近记忆用于没有命中检索时兜底。 rows self.conn.execute( SELECT content FROM memories ORDER BY id DESC LIMIT ?, (limit,) ).fetchall() return [row[0] for row in rows] def close(self): self.conn.close()这个模块先用了 SQLite 做持久化检索方式是最简单的LIKE模糊匹配。优点是零依赖、开箱即用缺点是无法理解语义。比如用户说“我家猫最近生病了”你用关键词“猫”只能匹配到含“猫”字的历史记录匹配不到“年糕”这种宠物名。生产环境建议接入 embedding 向量检索。4.6 编写核心 Agent创建agent.py# 文件路径simulator/agent.py from typing import Dict, List from openai import OpenAI from config import Config from memory import MemoryStore from persona import PersonaManager class SessionStore: 简单会话历史存储使用字典做内存缓存。 生产场景建议使用 Redis 等中间件。 def __init__(self, max_history: int 10): self.sessions: Dict[str, List[Dict]] {} self.max_history max_history def add_message(self, session_id: str, role: str, content: str): if session_id not in self.sessions: self.sessions[session_id] [] self.sessions[session_id].append( {role: role, content: content} ) # 简单滑动窗口保留最近 max_history*2 条消息 if len(self.sessions[session_id]) self.max_history * 2: self.sessions[session_id] self.sessions[session_id][-self.max_history * 2:] def get_history(self, session_id: str) - List[Dict]: return self.sessions.get(session_id, []) def clear(self, session_id: str): self.sessions.pop(session_id, None) class HumanSimulatorAgent: def __init__(self): self.config Config() self.client OpenAI( api_keyself.config.API_KEY, base_urlself.config.BASE_URL, ) self.persona_manager PersonaManager() self.memory_store MemoryStore(db_pathstr(self.config.MEMORY_DB)) self.session_store SessionStore(max_historyself.config.MAX_HISTORY) def _build_messages(self, session_id: str, user_input: str) - List[Dict]: # 1. 从长期记忆中召回相关内容 long_term_memories self.memory_store.search_memory(user_input, limit3) # 2. 如果召回结果不足补充最近记忆 if len(long_term_memories) 3: recent self.memory_store.recent_memories(limit3 - len(long_term_memories)) long_term_memories.extend(recent) # 3. 构建系统提示词 system_prompt self.persona_manager.build_system_prompt( long_term_memorieslong_term_memories ) # 4. 获取当前会话历史 history self.session_store.get_history(session_id) # 5. 组装消息列表 messages [{role: system, content: system_prompt}] messages.extend(history) messages.append({role: user, content: user_input}) return messages def chat(self, session_id: str, user_input: str) - str: # 记录用户消息 self.session_store.add_message(session_id, user, user_input) # 组装消息 messages self._build_messages(session_id, user_input) # 调用大模型 resp self.client.chat.completions.create( modelself.config.MODEL_NAME, messagesmessages, temperatureself.config.TEMPERATURE, ) reply resp.choices[0].message.content.strip() # 记录模型回复 self.session_store.add_message(session_id, assistant, reply) # 写入长期记忆 # 生产中建议做异步化、去重和摘要 self.memory_store.add_memory(f用户咨询{user_input[:80]}) self.memory_store.add_memory(fAI 回复{reply[:100]}) return reply def reset(self, session_id: str): self.session_store.clear(session_id) if __name__ __main__: agent HumanSimulatorAgent() while True: user_input input(你: ) if user_input.strip().lower() in (exit, quit, 退出): break reply agent.chat(console-demo, user_input) print(fAI: {reply})在这个 Agent 里我把“记忆召回”和“消息组装”分离这是比较清晰的结构。chat方法负责完整链路reset方法用于清空会话历史。注意这里把长期记忆做了“全量写入”每次对话都会把用户输入和 AI 回复写进数据库。生产环境这样做会带来很多脏数据需要做重要性判断、去重和摘要后面最佳实践会细说。4.7 编写 FastAPI 接口创建api.py# 文件路径simulator/api.py from fastapi import FastAPI from pydantic import BaseModel from agent import HumanSimulatorAgent app FastAPI(titleAI Human Simulator API, version0.1.0) agent HumanSimulatorAgent() class ChatRequest(BaseModel): message: str session_id: str default class ChatResponse(BaseModel): reply: str session_id: str app.post(/chat, response_modelChatResponse) def chat(req: ChatRequest): reply agent.chat(req.session_id, req.message) return ChatResponse(replyreply, session_idreq.session_id) app.get(/health) def health(): return {status: ok}这个接口的入参有两个message是用户消息session_id是用户/会话标识。使用session_id区分不同用户避免记忆互相串台。4.8 运行与验证启动服务cd simulator uvicorn api:app --host 0.0.0.0 --port 8000打开另一个终端用 curl 测试curl -X POST http://localhost:8000/chat \ -H Content-Type: application/json \ -d {session_id: user123, message: 你好请用一段话介绍你自己}预期返回结构类似{ reply: 你好我是小林一名喜欢折腾大模型和 Agent 的软件工程师。平时我会写写代码、听音乐、跑跑步最喜欢的事情就是研究怎么让 AI 更懂人类。你今天想聊点什么, session_id: user123 }如果你配置的模型和 API Key 正常那这个最小系统就已经跑通了。你还可以在同一个session_id下继续发送消息比如“我叫小红记住我是一名产品经理”过几分钟再问“我叫什么”它会通过长期记忆库回答你。5. 常见问题与排查思路在开发 AI 人类模拟器的过程中大部分问题并不神秘无非是提示词、上下文、记忆、API 调用这几类。下面整理成表格方便快速定位。问题现象常见原因解决思路回复不像设定的人设系统提示词信息太少或人设被长对话稀释丰富人设字段把相似描述改为一句话指令压缩历史对话超过模型上下文限制未对短期记忆做截断采用滑动窗口控制历史消息条数做历史摘要角色漂移前后矛盾长期记忆没有持续强化定期把关键信息写入长期记忆并在 system 中召回API 返回 429 限流请求过于频繁增加指数退避重试限制并发接入 Redis 缓存对话空洞、车轱辘话温度设置太高或上下文重复内容太多调低 temperature对记忆内容做去重所有用户记忆互相污染未使用 session_id / user_id 隔离按照用户维度隔离短期和长期存储模型答案编造事实没有给模型“不知道”的许可在 system 提示词中明确“不确定时要承认”下面展开几个典型问题的排查步骤。5.1 为什么 AI 慢慢就不像那个“人”了这是角色模拟最常见的问题叫“角色漂移”Persona Drift。原因是模型在长对话中越后面的 Token 权重可能越低早期 system 提示词的影响会被稀释。排查思路确认 system 提示词没有被裁减。确认历史消息中是否有其他角色身份的干扰内容。在每次对话前重新注入高权重人设摘要。考虑使用模型微调把固定人设固化成模型权重。5.2 长期记忆为什么没有被召回如果数据库里明明有“用户叫小红”但模型却说不知道常见原因是检索没有命中。排查思路检查search_memory能否通过 LIKE 查询到数据。如果用户输入里没有“小红”这个关键词模糊匹配无效需要升级为向量检索。补充最近记忆作为召回兜底但不能完全依赖。5.3 API 调用报错怎么定位当遇到AuthenticationError、RateLimitError、APIConnectionError时先区分是配置问题还是服务问题401/403API Key 错误或者没有权限访问该模型。404模型名称不存在或者 base_url 不对。429请求频率超限需要做退避重试。网络超时检查服务器能否访问目标接口地址。建议在config.py中打印脱敏后的BASE_URL和MODEL_NAME便于快速排查。6. 最佳实践与工程建议从 Demo 到可以上线的产品中间还有很长的路。下面这些建议来自实际场景中的通用经验适合你在项目迭代时逐步加入。6.1 人格档案化配置与代码分离不要把大段人设写在代码里推荐用 JSON、YAML 或数据库保存不同角色对应不同档案。这样产品运营可以随时调整人设不需要发版。例如// 文件路径simulator/personas/game_npc_001.json { name: 酒馆老板, persona_id: game_npc_001, version: 1.2.0, role: 边境小镇酒馆老板, background: 年轻时当过冒险者现在经营一家小酒馆消息灵通性格豪爽。, personality: [豪爽, 谨慎, 爱讲故事], speaking_style: 多用俚语喜欢在话语中暗示一些情报。, knowledge_bases: [游戏世界观, 酒馆传闻], temperature: 0.9 }6.2 记忆分层避免“全量存储脏数据”目前的示例把所有对话都写入长期记忆这会导致数据库快速膨胀且无关记忆会稀释重要信息。工程上建议做三层短期会话层滑动窗口保存最近 N 轮对话。场景记忆层每次对话结束后用摘要模型把重要信息提取出来。长期事实层只保存经过抽取、去重、评分后的事实例如“用户生日”“用户宠物名字”“用户近期目标”。6.3 内容安全与合规边界这一点非常重要尤其是做“人类模拟器”这种产品形态时不得用 AI 冒充真实自然人尤其是未经授权的公众人物。如果产品面向 C 端用户必须明确告知用户“你在和 AI 对话”。对用户输入和模型输出都要做内容审核设置敏感词库和违规内容拦截。涉及用户个人信息时要遵循最小化原则不支持随意长期留存需要提供删除机制。从技术角度建议在等模型调用前后增加一层审核逻辑。如果使用国内大模型通常服务商也提供内容安全接口可以直接对接。6.4 成本控制缓存、摘要与模型路由对话类应用的成本大头是 Token。假设一个用户每天聊 100 条消息每条消息都携带 10 条历史记录一个月下来的 Token 消耗会非常可观。控制成本的常用手段缓存命中对高频问题使用缓存不重复调用大模型。历史摘要当会话超过窗口时用模型把旧历史压缩成摘要替代全量记录。模型路由简单问答用轻量模型复杂推理用高级模型。动态减少记忆条数系统提示词中的长期记忆不是越多越好按相关度只取 Top 3-5 条。6.5 可观测性与日志上线后如果用户反馈“AI 突然变了一个人”没有日志很难排查。建议至少记录session_id、user_id。模型名称、温度参数、上下文 token 数量。组装后的 system 提示词。最终生成的回复。调用耗时、是否触发重试。日志中注意脱敏不要记录 API Key、完整对话中的敏感信息。6.6 从单体 Demo 走向生产架构示例代码把所有逻辑放在一个进程里生产环境建议拆分为客户端 - API 网关 - 模拟器服务 - LLM Provider | - 记忆服务向量库/Redis - 内容审核服务 - 数据仓库模拟器服务可以无状态化会话状态放到 Redis长期记忆放到向量数据库这样就能水平扩展。6.7 扩展 Agent 能力如果你希望模拟器不只是“聊天”还要能“做事”可以引入 Function Calling。例如查询天气、查询日历。调起搜索获取实时信息。发邮件、设置提醒。访问企业内部知识库。实现方式是在请求大模型时声明工具函数模型在需要时会返回一个函数调用请求由你的代码执行工具后再把结果返回给模型。这是目前做 AI Agent 的通用模式。7. 总结与学习路线写到这你已经从概念、原理、代码和工程实践四个维度理解了 AI 人类模拟器的技术骨架。核心收获是这句话大模型本身只是一块通用的“推理引擎”所谓“人类模拟器”的价值完全取决于你对人设的管理、对记忆的设计、对交互链路的编排。如果你打算继续深入可以按下面的路线走先把本文代码跑通感受人设提示词对输出风格的影响。然后把长期记忆从 SQLite 换成向量数据库接入文本 embedding实现语义召回。再引入 Function Calling让模拟器具备工具调用能力。继续接 TTS 和数字人形象形成完整的语音交互闭环。最后考虑多 Agent 协作比如“主持人 嘉宾 观众”的多角色模拟器。在实际项目中优先关注三件事内容合规边界、用户隐私保护、Token 成本控制。这三点决定了一个 AI 陪伴/数字人产品能不能长期运营下去。技术演进很快但底层套路是稳定的人格化 Prompt 记忆系统 模型调用 工程化治理。掌握这套最小闭环你就有能力在 AI 应用层做出自己的东西。希望这份最小实现能成为你进入 AI 人类模拟器开发的起点。