每年春节,「叫人」这件事都会难倒一批年轻人。尤其是常年在外、难得回老家的那种,面对七大姑八大姨,话到嘴边叫不出声——不是不懂礼貌,是真不知道该喊什么。
于是我自己写了一个工具:who.52stu.com。
输入一段亲戚关系描述,它能告诉你正确的称呼。比如"妈妈的姐姐的老公"是"姨父","爸爸的弟弟的孙女"是"堂侄女"。目前支持1000多种亲戚关系组合,够覆盖绝大部分日常场景。

核心是代数累加模型
开发这个工具的过程,比我想象中复杂。一开始我也想过偷懒——做个数据库,把所有关系都存进去,查询时直接匹配不就完了?
后来发现这条路走不通。中国亲戚关系太复杂了,光"舅舅的儿子"就有好几种叫法:可能是"表弟",也可能是"表舅",取决于对方年龄和自己的相对关系。枚举所有情况,数据量会爆炸,而且永远有遗漏。
真正的解决方案是一套代数系统。
每个亲戚都有一个"代数"(gen)值:
- 祖辈:gen = -1, -2……
- 自己:gen = 0
- 子辈:gen = +1, +2……
从自己出发,沿着关系链累加代数,就能算出对方和自己差几代。比如"奶奶的哥哥的儿子":先到奶奶(gen=-1),再到奶奶的哥哥(再-1=-2),最后到他的儿子(+1=-1),结论是比自己高一辈,是"表叔"。

代数累加能解决80%的问题,但剩下的20%才是噩梦。
那些没法用公式处理的边界情况
母系和父系的区分是第一个坑。"舅舅"和"叔叔"代数相同,但一个是妈妈那边的,一个是爸爸那边的。这种区分在代数上看不出来,必须单独处理。
堂表之分更复杂。同是表亲,姑姑家的、姨妈家的、舅舅家的,叫法可能不同(虽然很多地方已经混用了)。同是堂亲,伯伯家的和叔叔家的理论上也有区别。
年龄判断是个玄学。上一代的男性,该叫"哥"还是"叔"?答案取决于对方比你大还是小。但算法没有你的年龄数据。工具的做法是列出多个可能结果,让用户自行选择。
还有一个处理起来很烦但技术上不难的问题:合称。"父母"其实是"父亲+母亲"的合称,"兄弟姐妹"要拆成"哥哥/弟弟/姐姐/妹妹"。加个预处理逻辑就能解决。
这些边界情况花了我大部分开发时间。核心算法可能200行就能写完,但特殊规则处理写了将近2000行。
做这个工具的一些想法
为什么非要自己做?因为我查过市面上已有的方案,大多只能处理简单的父子关系,稍微复杂一点就报错。用户真正需要的,恰恰是这些"非标准"场景。
开发过程中最让我意外的是:很多我以为"理所当然"的亲戚知识,其实很难用规则描述。比如"大伯"和"叔叔"的区别——理论上前者指父亲的哥哥,后者指父亲的弟弟,但实际使用中很多人根本不区分。如果工具严格按规则来,反而会被用户骂"不准"。
所以我加了一层"模糊匹配":当规则匹配失败时,尝试找最接近的结果。这让准确率从80%提升到了95%以上。
工具已经开源,依赖的是 relationship.js 这个库。代码在 GitHub 上,有兴趣的可以看看,也欢迎提 issue 和 PR。




