1. 项目背景与核心价值
春节回家最怕什么?不是七大姑八大姨的催婚,而是突然被问到"这是你表叔家的二儿子的媳妇的妹妹,你该叫什么?"这种灵魂拷问。作为一个在北方长大、后来定居南方的"移民",我深刻体会到中国亲属称谓系统的复杂性——光是"舅舅"在南北方的不同叫法就能让人晕头转向。
这个"亲戚计算器"项目正是为了解决这个痛点而生。它不仅能快速计算任意两人之间的亲属关系称谓,还内置了南北方差异对照功能。去年春节我用初版测试时,成功避免了把"姑奶奶"叫成"姨姥姥"的社死现场,从此成为家族聚会的救命神器。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 功能设计与实现原理
2.1 亲属关系建模
核心数据结构采用有向图模型,每个节点包含:
- 基础属性:性别、辈分、年龄差
- 关系边:夫妻、亲子、兄弟姐妹三种基础关系
- 扩展属性:存续情况(用于区分继亲/养亲等特殊关系)
python复制class FamilyMember:
def __init__(self, uid, name, gender, generation):
self.uid = uid # 唯一标识符
self.name = name
self.gender = gender # 0女 1男
self.generation = generation # 辈分值
self.relations = [] # 关系边
class Relation:
def __init__(self, rel_type, target, is_direct=True):
self.type = rel_type # 1夫妻 2亲子 3兄弟姐妹
self.target = target # 目标成员UID
self.is_direct = is_direct # 是否直系
2.2 路径搜索算法
采用改进的BFS算法,在搜索时同步记录:
- 路径中的性别序列(用于区分叔/姑等称谓)
- 代际变化方向(区分上行/下行称谓)
- 转折点标记(如"表亲"关系的识别点)
python复制def find_relation_path(start_uid, end_uid):
queue = deque([(start_uid, [])])
visited = set()
while queue:
current_uid, path = queue.popleft()
if current_uid == end_uid:
return path
for rel in family_graph[current_uid].relations:
if rel.target not in visited:
new_path = path + [rel]
queue.append((rel.target, new_path))
visited.add(rel.target)
return None # 未找到路径
3. 南北方差异处理方案
3.1 称谓映射表设计
建立双层映射体系:
- 基础关系码(如"fathers_older_brother")
- 方言称谓字典:
json复制{ "mandarin": {"fathers_older_brother": "伯父"}, "cantonese": {"fathers_older_brother": "阿伯"}, "sichuan": {"fathers_older_brother": "伯伯"} }
3.2 自动检测逻辑
- 根据用户IP初步判断地域
- 提供手动切换选项
- 记忆用户最后使用偏好
4. 实战避坑指南
4.1 特殊关系处理
- 继亲关系:需要明确标注"继"字(如继母)
- 养子女:建议单独标记避免混淆
- 同父异母:在关系边添加备注字段
4.2 性能优化
当家族成员超过500人时:
- 采用层级分区索引
- 预计算常见关系路径
- 实现懒加载机制
5. 前端交互设计技巧
5.1 可视化家谱
使用力导向图展示关系网络,关键配置:
javascript复制const simulation = d3.forceSimulation(nodes)
.force("link", d3.forceLink(links).id(d => d.id))
.force("charge", d3.forceManyBody().strength(-500))
.force("x", d3.forceX().strength(0.1))
.force("y", d3.forceY().strength(0.1));
5.2 智能输入建议
实现基于前缀树的快速检索:
python复制class TrieNode:
def __init__(self):
self.children = {}
self.is_end = False
def search_prefix(root, prefix):
node = root
for char in prefix:
if char not in node.children:
return []
node = node.children[char]
return _get_all_words(node, prefix)
6. 隐私保护方案
- 本地存储优先:所有家谱数据默认存储在IndexedDB
- 云端同步需二次确认
- 敏感关系(如非婚生子女)支持加密备注
7. 扩展应用场景
- 小说创作辅助:快速构建人物关系网
- 族谱数字化:对接老式族谱图片OCR识别
- 法律咨询:自动生成亲属关系证明模板
这个项目最让我意外的收获是:很多年轻用户用它来理解《红楼梦》里复杂的人物关系。有位中学老师甚至开发了教学模块,用可视化关系图讲解古典文学中的家族体系。
