From 16b476167e42bf9a2698288800e789e057e2f01b Mon Sep 17 00:00:00 2001 From: Chen Yi <466354947@qq.com> Date: Mon, 5 Oct 2026 22:39:53 +0800 Subject: [PATCH] =?UTF-8?q?=E4=B8=93=E5=90=8D=E6=9C=AC=E5=9C=9F=E5=8C=96?= =?UTF-8?q?=EF=BC=88=E4=BF=A1=E8=BE=BE=E9=9B=85=EF=BC=89=EF=BC=9A=E5=86=BB?= =?UTF-8?q?=E7=BB=93=E8=AF=91=E5=90=8D=E8=A1=A8=20+=20=E6=B8=B2=E6=9F=93?= =?UTF-8?q?=E5=B1=82=EF=BC=8C=E5=B9=B6=E4=BF=AE=E6=8E=89=E6=A0=A1=E9=AA=8C?= =?UTF-8?q?=E5=99=A8=E7=9A=84=E6=AD=A3=E5=88=99=E7=9B=B2=E7=82=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 新增 dfannals/glossary.py(译名表)与 dfannals/localize.py(渲染层) 人名=音译+绰号意译(Ral Fastenhatchets→拉尔·缚斧、朗古德·商熊「剖胎之寒」), 地名整体意译(Fordedwinds→涉风渡、The Volcano Of Ravens→渡鸦火山) - 生成链路本土化:素材渲染、人物表、扩写白名单全部走译名;已有产物做确定性替换 - 修复 factcheck 的 \b 盲点:Unicode 下汉字也算词字符,紧贴汉字的英文名不被检查 (曾因此漏掉编造专名)。修好后抓出并定点修掉长版第 1 集的 2 处编造 - 修正 title_form 大小写(YETI→Yeti),此前 Yeti/Goblin 一直漏译 - 新增 tests/test_localize.py(13 项回归) --- dfannals/cast.py | 5 +- dfannals/expand.py | 10 +- dfannals/factcheck.py | 5 +- dfannals/glossary.py | 208 ++++++++++++ dfannals/localize.py | 240 ++++++++++++++ dfannals/volume.py | 7 +- output/volumes/v1/cast.md | 38 +-- .../v1/chapters/001-181-198.literary.md | 312 +++++++++--------- output/volumes/v1/chapters/001-181-198.md | 36 +- output/volumes/v1/chapters/002-202-216.md | 30 +- output/volumes/v1/chapters/003-219-228-p1.md | 18 +- output/volumes/v1/figures.md | 218 ++++++------ output/volumes/v1/timeline.md | 28 +- tests/test_localize.py | 119 +++++++ 14 files changed, 924 insertions(+), 350 deletions(-) create mode 100644 dfannals/glossary.py create mode 100644 dfannals/localize.py create mode 100644 tests/test_localize.py diff --git a/dfannals/cast.py b/dfannals/cast.py index bd1d0df..074cfd3 100644 --- a/dfannals/cast.py +++ b/dfannals/cast.py @@ -15,7 +15,7 @@ import re from dataclasses import dataclass from pathlib import Path -from dfannals import factcheck +from dfannals import factcheck, localize from dfannals.config import MAX_TOKENS_STRUCTURED, Gateway from dfannals.episodes import Episode from dfannals.legends import Event, World @@ -221,7 +221,8 @@ def build_cast( "", ] - return "\n".join(lines) + "\n", rows, suspicions + # 专名本土化:表格与小传都输出中文译名 + return localize.for_world(world).render("\n".join(lines)) + "\n", rows, suspicions def write_cast(path: Path, text: str) -> Path: diff --git a/dfannals/expand.py b/dfannals/expand.py index a4daa20..97d5df0 100644 --- a/dfannals/expand.py +++ b/dfannals/expand.py @@ -18,7 +18,7 @@ from collections import Counter from dataclasses import replace from pathlib import Path -from dfannals import deslop, volume +from dfannals import deslop, localize, volume from dfannals import episodes as ep_mod from dfannals.chronicle import cjk_length from dfannals.config import ( @@ -100,14 +100,16 @@ def allowed_names(world: World, thread: Thread, episode: ep_mod.Episode) -> list names.add(name) figure = world.figures.get(fid) if figure and figure.race: - names.add(figure.race) - names.add(_title_form(figure.race)) + # 种族值也要给中文:模型引到雪人、鹰人这类词时不能写成新角色 + names.add(localize.translate_race(figure.race)) for event in episode.events: for ref in world.render_refs(event): value = ref.partition("=")[2].strip() if value: names.add(value) - return sorted(n for n in names if n) + # 全部过一遍译名表:白名单里必须是正文里真正会出现的写法 + translator = localize.for_world(world) + return sorted({tr for tr in (translator.render(n).strip() for n in names) if tr}) def chunk_messages( diff --git a/dfannals/factcheck.py b/dfannals/factcheck.py index 9651417..875908d 100644 --- a/dfannals/factcheck.py +++ b/dfannals/factcheck.py @@ -35,7 +35,10 @@ COMMON_WORDS = { } # 拉丁专名序列:首字母大写的词,可含 ' - 与数字 -NAME_RE = re.compile(r"\b[A-Z][A-Za-z'\-]*(?:\s+[A-Z][A-Za-z'\-]*)*\b") +# 英文专名的边界不能用 \b:Unicode 下汉字也算「词字符」,于是 `在Mistbreath的` +# 这种紧贴汉字的英文名根本不会被匹配——实测正是这个盲点让一个编造的地名混过了校验。 +# 改成前后看「是不是英文字母」,与汉字相邻也能抓到。 +NAME_RE = re.compile(r"(? tuple[str, str]: + """拆出 DF 的长称号:`Xxx Yyy the Zzz Of Www` → ('Xxx Yyy', 'the zzz of www')。""" + lowered = name.strip().lower() + marker = " the " + if marker in lowered: + main, epithet = lowered.split(marker, 1) + return main, "the " + epithet + return lowered, "" + + +def translate_person(name: str) -> str | None: + """人名:名字音译 + 姓氏意译。查不全就返回 None(宁可保留英文)。""" + if not name: + return None + main, epithet = split_epithet(name) + parts = _WORD_SPLIT.split(main) + stem = glossary.STEMS.get(parts[0]) + if stem is None: + return None + surname = "" + if len(parts) > 1: + surname = glossary.SURNAMES.get("".join(parts[1:]), "") + if not surname: + return None + out = stem if not surname else f"{stem}·{surname}" + if epithet: + out += "「" + glossary.EPITHETS.get(epithet, "") + "」" + if not glossary.EPITHETS.get(epithet): + return None + return out + + +def translate_place(name: str) -> str | None: + """地名:整体意译;带称号的写成「主名(称号)」。""" + if not name: + return None + main, epithet = split_epithet(name) + base = glossary.PLACES.get(main.replace(" ", "")) + if base is None: + return None + if epithet: + extra = glossary.EPITHETS.get(epithet) + return f"{base}({extra})" if extra else None + return base + + +def translate_group(name: str) -> str | None: + if not name: + return None + return glossary.GROUPS.get(name.strip().lower()) + + +def translate_race(value: str) -> str: + """种族值(DWARF、EAGLE_MAN)→ 中文;查不到原样返回。""" + if not value: + return value + return glossary.RACES.get(value.strip().upper(), value) + + +def translate_site_type(value: str) -> str: + if not value: + return value + return glossary.SITE_TYPES.get(value.strip().lower(), value) + + +@dataclass +class Translator: + """把一整个世界的专名译好,供渲染与校验共用。""" + + people: dict[str, str] = field(default_factory=dict) # 英文原名 → 中文 + places: dict[str, str] = field(default_factory=dict) + groups: dict[str, str] = field(default_factory=dict) + stems: dict[str, str] = field(default_factory=dict) # 单用名(正文里绝大多数是简称) + surnames: dict[str, str] = field(default_factory=dict) # 单用姓(对白里互相叫姓) + races: dict[str, str] = field(default_factory=dict) # 含全大写与首字母大写两种写法 + pending: list[str] = field(default_factory=list) # 表里没有、原样保留的名字 + + def person(self, name: str) -> str: + return self.people.get(name, name) + + def place(self, name: str) -> str: + return self.places.get(name, name) + + def group(self, name: str) -> str: + return self.groups.get(name, name) + + def _pairs(self) -> list[tuple[str, str]]: + """按英文原名长度降序:先替换长的,避免 `Ral` 抢在 `Ral Fastenhatchets` 前面。 + + 顺序很重要:全名 → 单独的姓 → 单独的名。换掉全名后正文里已无拉丁字母, + 后面两步不会再动它。 + """ + full = list(self.people.items()) + list(self.places.items()) + list(self.groups.items()) + full.sort(key=lambda kv: -len(kv[0])) + tail = list(self.surnames.items()) + list(self.stems.items()) + tail.sort(key=lambda kv: -len(kv[0])) + return full + tail + + def render(self, text: str) -> str: + """把已有正文里的英文专名换成中文,并收拾替换后多余的空格。""" + for source, target in self._pairs(): + text = re.sub(rf"(? set[str]: + """译名集合:事实校验要把它们当已知名字,否则会把译文当成凭空编造。""" + out: set[str] = set() + for target in [*self.people.values(), *self.places.values(), *self.groups.values()]: + out.add(target) + out.update(re.split(r"[·()「」,、]", target)) + return {name for name in out if name} + + def coverage(self) -> str: + rows = [ + ( + f"译名覆盖:人物 {len(self.people)} 个|地点 {len(self.places)} 个|" + f"势力 {len(self.groups)} 个" + ), + ] + if self.pending: + rows.append(f"待译(原样保留){len(self.pending)} 个:" + "、".join(self.pending[:12])) + return "\n".join(rows) + + +def tidy_spaces(text: str) -> str: + """去掉中日韩字符之间被替换后留下的空格:`拉尔 说` → `拉尔说`。 + + 英文专名之间、以及英文与汉字之间的空格保留(`Ral Fastenhatchets` 用得上)。 + """ + text = re.sub(rf"(?<=[{_CJK}])[ \t]+(?=[{_CJK}])", "", text) + text = re.sub(rf"(?<=[{_CJK}])[ \t]+(?=[,。、;:!?)】」])", "", text) + text = re.sub(rf"(?<=[(【「])[ \t]+(?=[{_CJK}])", "", text) + return text + + +def title_form(value: str) -> str: + """YETI → Yeti、EAGLE_MAN → Eagle_man、fastenhatchets → Fastenhatchets。 + + 两个坑都踩过: + - 只改首字母不转小写,`YETI` 会得到 `YETI`,永远匹配不上正文里的 `Yeti`; + - 按下划线逐段首字母大写,`EAGLE_MAN` 会得到 `Eagle_Man`, + 而史料渲染惯例是 `Eagle_man`(见 legends.pretty)。 + """ + lowered = value.lower() + return lowered[:1].upper() + lowered[1:] + + +def build(world: World) -> Translator: + """按世界里的实际名字建翻译器。""" + translator = Translator() + # 名与姓都单独收一份:正文里大量使用简称("Ral")和对白里只呼姓("Fastenhatchets") + translator.stems = {title_form(en): zh for en, zh in glossary.STEMS.items()} + translator.surnames = {title_form(en): zh for en, zh in glossary.SURNAMES.items()} + translator.races = {} + for en, zh in glossary.RACES.items(): + translator.races[en] = zh + translator.races[title_form(en)] = zh + # 逐段大写的写法(Eagle_Man)也登记:模型两种都可能写 + translator.races["_".join(p[:1].upper() + p[1:].lower() for p in en.split("_"))] = zh + for figure in world.figures.values(): + raw = figure.name + if not raw: + continue + translated = translate_person(raw) + shown = _display(raw) + if translated: + translator.people[shown] = translated + translator.people[raw] = translated + elif _WORD_SPLIT.split(shown.lower())[0] in glossary.STEMS: + # 名字能读、姓氏没词条:这是真正需要补的缺口,登记下来 + translator.pending.append(shown) + for site in world.sites.values(): + raw = site.name + if not raw: + continue + translated = translate_place(raw) + shown = _display(raw) + if translated: + translator.places[shown] = translated + translator.places[raw] = translated + for entity in world.entities.values(): + raw = entity.name + if not raw: + continue + translated = translate_group(raw) + shown = _display(raw) + if translated: + translator.groups[shown] = translated + translator.groups[raw] = translated + return translator + + +_CACHE: dict[int, tuple[World, Translator]] = {} + + +def for_world(world: World) -> Translator: + """带缓存的建立器:一次运行里反复渲染素材,不能每次都重建 4 万个人名。""" + hit = _CACHE.get(id(world)) + if hit is not None and hit[0] is world: + return hit[1] + translator = build(world) + _CACHE[id(world)] = (world, translator) + return translator + + +def _display(raw: str) -> str: + """史料的程序化名全小写,渲染层会做首字母大写;译名要按展示形式建索引。""" + from dfannals.legends import pretty + + return pretty(raw) diff --git a/dfannals/volume.py b/dfannals/volume.py index f6cb095..c2f680b 100644 --- a/dfannals/volume.py +++ b/dfannals/volume.py @@ -12,7 +12,7 @@ from dataclasses import dataclass, replace from pathlib import Path from dfannals import episodes as ep_mod -from dfannals import gate +from dfannals import gate, localize from dfannals.cast import collect_rows from dfannals.chronicle import cjk_length from dfannals.config import ( @@ -194,12 +194,13 @@ def render_material( "", "### 写作要求", "", - f"- 本集 {CHAPTER_MIN_CHARS}–{CHAPTER_MAX_CHARS} 字,中文正文,专名保留英文。", + f"- 本集 {CHAPTER_MIN_CHARS}–{CHAPTER_MAX_CHARS} 字,中文正文,人名地名用上面给出的中文译名。", "- 贴着主角写:他们的目标、算计、得失做主语;对手要是个具体的人。", "- 性别按上面卡片写,不要默认“他”;史料未载性别时用名字或身份称呼。", "- 史料之外的世界大事不要写;只有影响到主角时才提一句。", ] - return "\n".join(lines) + # 专名本土化:素材里的英文原名换成中文译名,让模型直接用中文写 + return localize.for_world(world).render("\n".join(lines)) def build_messages( diff --git a/output/volumes/v1/cast.md b/output/volumes/v1/cast.md index a57e559..bc50aa0 100644 --- a/output/volumes/v1/cast.md +++ b/output/volumes/v1/cast.md @@ -1,37 +1,37 @@ # Mon Sagus · 人物表 -本卷主角线索:Guspu Frillyknots、Ral Fastenhatchets、Alath Blottedmine +本卷主角线索:古斯普·褶结、拉尔·缚斧、阿拉斯·污矿 线索跨度:181–248 | 人物 | 种族 | 性别 | 生卒 | 身份 | 本卷出场 | 角色 | |---|---|---|---|---|---|---| -| Guspu Frillyknots | EAGLE_MAN | 男 | 151–246 | 关系对象×13、构陷发起者×4 | 62 | 主角 | -| Ral Fastenhatchets | DWARF | 女 | 164–在世/不详 | 被针对者×21、受骗者×6 | 28 | 主角 | -| Alath Blottedmine | DWARF | 男 | 182–在世/不详 | 构陷发起者×4、关系对象×1 | 8 | 主角 | -| Tulon Tongswall | DWARF | 男 | 132–在世/不详 | 构陷发起者×3 | 3 | 对手/配角 | -| Moldath Mirroredfloors | DWARF | 女 | 79–在世/不详 | 构陷发起者×3 | 3 | 对手/配角 | -| Ineth Wheeleddrinks | DWARF | 男 | 165–在世/不详 | 构陷者×3 | 3 | 对手/配角 | -| Langgud Tradebears The Eviscerated Chill Of Pregnancies | YETI | 男 | 生卒不详 | — | 2 | 对手/配角 | -| Rigoth Stilledearthen | DWARF | 男 | 162–在世/不详 | 当事者×2 | 2 | 对手/配角 | -| Perom Crazeowned | HUMAN | 男 | 129–在世/不详 | 当事者×1、关系对象×1 | 2 | 对手/配角 | +| 古斯普·褶结 | 鹰人 | 男 | 151–246 | 关系对象×13、构陷发起者×4 | 62 | 主角 | +| 拉尔·缚斧 | 矮人 | 女 | 164–在世/不详 | 被针对者×21、受骗者×6 | 28 | 主角 | +| 阿拉斯·污矿 | 矮人 | 男 | 182–在世/不详 | 构陷发起者×4、关系对象×1 | 8 | 主角 | +| 图隆·钳墙 | 矮人 | 男 | 132–在世/不详 | 构陷发起者×3 | 3 | 对手/配角 | +| 莫尔达斯·镜层 | 矮人 | 女 | 79–在世/不详 | 构陷发起者×3 | 3 | 对手/配角 | +| 伊内斯·轮饮 | 矮人 | 男 | 165–在世/不详 | 构陷者×3 | 3 | 对手/配角 | +| 朗古德·商熊「剖胎之寒」 | 雪人 | 男 | 生卒不详 | — | 2 | 对手/配角 | +| 里戈斯·静土 | 矮人 | 男 | 162–在世/不详 | 当事者×2 | 2 | 对手/配角 | +| 佩罗姆·狂据 | 人类 | 男 | 129–在世/不详 | 当事者×1、关系对象×1 | 2 | 对手/配角 | ## 小传 -**Guspu Frillyknots** —— 鹰人Guspu Frillyknots以六十二次出场与十三次关系对象记录高踞本卷,193年在Fordedwinds对Ral Fastenhatchets构陷未遂,次年被The Volcano Of Ravens定罪。 +**古斯普·褶结** —— 鹰人古斯普·褶结以六十二次出场与十三次关系对象记录高踞本卷,193年在涉风渡对拉尔·缚斧构陷未遂,次年被渡鸦火山定罪。 -**Ral Fastenhatchets** —— 矮人Ral Fastenhatchets是本卷最执拗的靶子:181年与Langgud Tradebears The Eviscerated Chill Of Pregnancies在Fordedwinds两度交手,此后Guspu、Tulon、Alath、Moldath与Ineth轮番构陷或诬告,均未得逞;她与Rigoth Stilledearthen的关系于219年解除。 +**拉尔·缚斧** —— 矮人拉尔·缚斧是本卷最执拗的靶子:181年与朗古德·商熊「剖胎之寒」在涉风渡两度交手,此后古斯普、图隆、阿拉斯、莫尔达斯与伊内斯轮番构陷或诬告,均未得逞;她与里戈斯·静土的关系于219年解除。 -**Alath Blottedmine** —— 矮人Alath Blottedmine于229年对Ral Fastenhatchets、230年对Momuz Decentpage构陷未遂,并与Sina Watchedleads、Artuk Huggedfastened有过关系记录;230年被The Volcano Of Ravens定罪。 +**阿拉斯·污矿** —— 矮人阿拉斯·污矿于229年对拉尔·缚斧、230年对莫穆兹·端页构陷未遂,并与西娜·守铅、阿图克·抱固有过关系记录;230年被渡鸦火山定罪。 -**Tulon Tongswall** —— 矮人Tulon Tongswall在193、195、197年连续三次于Fordedwinds构陷Ral Fastenhatchets,三次全败,出场也仅此三回。 +**图隆·钳墙** —— 矮人图隆·钳墙在193、195、197年连续三次于涉风渡构陷拉尔·缚斧,三次全败,出场也仅此三回。 -**Moldath Mirroredfloors** —— 矮人Moldath Mirroredfloors在233年两度、234年一度于Fordedwinds构陷Ral Fastenhatchets,均告失败,算本卷坚韧而无效的对手之一。 +**莫尔达斯·镜层** —— 矮人莫尔达斯·镜层在233年两度、234年一度于涉风渡构陷拉尔·缚斧,均告失败,算本卷坚韧而无效的对手之一。 -**Ineth Wheeleddrinks** —— 矮人Ineth Wheeleddrinks在245、247、248年三次对Ral Fastenhatchets发起诬告,均告失败,The Volcano Of Ravens始终未予采信。 +**伊内斯·轮饮** —— 矮人伊内斯·轮饮在245、247、248年三次对拉尔·缚斧发起诬告,均告失败,渡鸦火山始终未予采信。 -**Langgud Tradebears The Eviscerated Chill Of Pregnancies** —— 雪人Langgud Tradebears The Eviscerated Chill Of Pregnancies于181年在Fordedwinds与Ral Fastenhatchets两度交手,生卒不详,除了名字长到令人侧目外只留下这两条战斗记录。 +**朗古德·商熊「剖胎之寒」** —— 雪人朗古德·商熊「剖胎之寒」于181年在涉风渡与拉尔·缚斧两度交手,生卒不详,除了名字长到令人侧目外只留下这两条战斗记录。 -**Rigoth Stilledearthen** —— 矮人Rigoth Stilledearthen于188年与Ral Fastenhatchets建立关系,219年解除,两条记录便写尽他在本卷的起落。 +**里戈斯·静土** —— 矮人里戈斯·静土于188年与拉尔·缚斧建立关系,219年解除,两条记录便写尽他在本卷的起落。 -**Perom Crazeowned** —— 人类Perom Crazeowned在193年与Guspu Frillyknots建立关系,202年又添一笔,是鹰人关系网中露面有限的配角。 +**佩罗姆·狂据** —— 人类佩罗姆·狂据在193年与古斯普·褶结建立关系,202年又添一笔,是鹰人关系网中露面有限的配角。 diff --git a/output/volumes/v1/chapters/001-181-198.literary.md b/output/volumes/v1/chapters/001-181-198.literary.md index dd29993..c0de1af 100644 --- a/output/volumes/v1/chapters/001-181-198.literary.md +++ b/output/volumes/v1/chapters/001-181-198.literary.md @@ -1,389 +1,389 @@ # 守门人 -181年的Fordedwinds还没有名字。 +181年的涉风渡还没有名字。 -那条隘口夹在两片黑石崖之间,冬季的河已经结死,冻得发青的冰面一直铺到山脚。Ral Fastenhatchets第一次踩上那道冰面的时候,脚下打了一个趔趄,铁头靴的底沿磕在石头茬子上,磕出一声闷响。她没抬头,伸手摸了一把刃口,把斧头从背上换到左手,顺着风向往前挪了两步。风向不对。从北面谷口直灌进来的冷气不自然,带着一股湿漉漉的腥味,像是某种大块头的活物刚在那儿蹲过不久。她把斧柄往掌心里攥紧了一点。 +那条隘口夹在两片黑石崖之间,冬季的河已经结死,冻得发青的冰面一直铺到山脚。拉尔·缚斧第一次踩上那道冰面的时候,脚下打了一个趔趄,铁头靴的底沿磕在石头茬子上,磕出一声闷响。她没抬头,伸手摸了一把刃口,把斧头从背上换到左手,顺着风向往前挪了两步。风向不对。从北面谷口直灌进来的冷气不自然,带着一股湿漉漉的腥味,像是某种大块头的活物刚在那儿蹲过不久。她把斧柄往掌心里攥紧了一点。 那个东西就在路口正中。 -两倍高。四层高的。一个Yeti。肩宽差不多能塞下她两个,灰白的长毛从肩胛一直垂到脚踝,每一根都结着霜。它坐在那儿,一条腿曲着,另一条直直伸出去,整个身子像是长在这块石头上。Langgud Tradebears The Eviscerated Chill Of Pregnancies。这名字是从哪儿听来的她记不清了——也许是哪个从南边林子里活着爬出去的猎人。她在意的是另一件事:这东西挡在Fordedwinds的入口,把南来北往的小路堵死了。 +两倍高。四层高的。一个雪人。肩宽差不多能塞下她两个,灰白的长毛从肩胛一直垂到脚踝,每一根都结着霜。它坐在那儿,一条腿曲着,另一条直直伸出去,整个身子像是长在这块石头上。朗古德·商熊「剖胎之寒」。这名字是从哪儿听来的她记不清了——也许是哪个从南边林子里活着爬出去的猎人。她在意的是另一件事:这东西挡在涉风渡的入口,把南来北往的小路堵死了。 她没退。 -她可以退回矿洞,退回那帮矮人的巷子里,把斧头挂上墙,告诉自己这事不该她管。矿洞里还有热汤,铁锅架在石灶上咕嘟响,老矿工还能在桌边骂上半夜的山。可她没走。她在隘口外二十步的地方站住了,把斧头从左手换回右手,刃口朝前。Langgud Tradebears的呼气从那团灰白的毛里一下一下地喷出来,每一次喷出去都能在它面前凝出一小片白雾。她感觉自己胡子尖上开始挂霜了。 +她可以退回矿洞,退回那帮矮人的巷子里,把斧头挂上墙,告诉自己这事不该她管。矿洞里还有热汤,铁锅架在石灶上咕嘟响,老矿工还能在桌边骂上半夜的山。可她没走。她在隘口外二十步的地方站住了,把斧头从左手换回右手,刃口朝前。朗古德商熊的呼气从那团灰白的毛里一下一下地喷出来,每一次喷出去都能在它面前凝出一小片白雾。她感觉自己胡子尖上开始挂霜了。 “让开。” -她说。声音从喉咙里挤出来,被冷空气一激,哑了半截。Yeti没动。她又往前走了一步,铁头磕在冻硬的泥地上,叮地响了一声。Yeti这才抬眼。两颗黑眼珠嵌在灰白毛里,慢悠悠地落到她脸上,没有立刻往上抬,也没有立刻往下移。 +她说。声音从喉咙里挤出来,被冷空气一激,哑了半截。雪人没动。她又往前走了一步,铁头磕在冻硬的泥地上,叮地响了一声。雪人这才抬眼。两颗黑眼珠嵌在灰白毛里,慢悠悠地落到她脸上,没有立刻往上抬,也没有立刻往下移。 -“让开。”她又说了一遍。这一次她没看Yeti的脸,看的是它前爪搭着的那块石头。那块石头底下压着半截骨头,骨头边上还冻着一摊发黑的什么,已经冻成冰茬子。这是上一个从这儿过的东西,或者上一个没能过去的人。她把目光从骨头上挪开,挪到Yeti的前爪边上。前爪指节上套着一圈磨秃的皮,皮上刻着一个符号,她认不出来。 +“让开。”她又说了一遍。这一次她没看雪人的脸,看的是它前爪搭着的那块石头。那块石头底下压着半截骨头,骨头边上还冻着一摊发黑的什么,已经冻成冰茬子。这是上一个从这儿过的东西,或者上一个没能过去的人。她把目光从骨头上挪开,挪到雪人的前爪边上。前爪指节上套着一圈磨秃的皮,皮上刻着一个符号,她认不出来。 -Langgud Tradebears The Eviscerated Chill Of Pregnancies没说话。它只是把那只前爪往石头上挪了挪,指节咔地响了一声。这是回答。不是答应,也不是拒绝,是告诉她:这块石头我占着,你拿来动它试试。 +朗古德·商熊「剖胎之寒」没说话。它只是把那只前爪往石头上挪了挪,指节咔地响了一声。这是回答。不是答应,也不是拒绝,是告诉她:这块石头我占着,你拿来动它试试。 -她没动斧头。她从腰后抽出那块她揣了整个早晨的石头,顺手丢到了路上。石头落在冰面上,滑出去两尺,撞上Yeti伸出的那只脚的脚背,咣地响了一声。Yeti低头看那块石头,又抬头看她。她站着,没弯腰,没退,铁头杵在脚边。她不打算解释这块石头是什么意思,不打算解释她为什么不打算退。她只是站着。 +她没动斧头。她从腰后抽出那块她揣了整个早晨的石头,顺手丢到了路上。石头落在冰面上,滑出去两尺,撞上雪人伸出的那只脚的脚背,咣地响了一声。雪人低头看那块石头,又抬头看她。她站着,没弯腰,没退,铁头杵在脚边。她不打算解释这块石头是什么意思,不打算解释她为什么不打算退。她只是站着。 -Yeti先动了。它把那条直着的腿收回来,整个身子往边上挪了半步。就半步。它侧过半边身子,前爪还搭在那块石头上,没让出整条路。它让出了她能侧身挤过去的那一点空隙。 +雪人先动了。它把那条直着的腿收回来,整个身子往边上挪了半步。就半步。它侧过半边身子,前爪还搭在那块石头上,没让出整条路。它让出了她能侧身挤过去的那一点空隙。 她没挤。 -她从那块石头上迈了过去,铁头靴的底沿磕在Yeti前爪的指节上,磕得指节上的皮圈咯吱响了一声。Yeti的毛抖了一下,没拍下来。她走过去了。她没回头看。她知道如果她回头看,那只前爪会在她后脑勺上拍一下,把她的头连骨带捅进冰里。她一直走到隘口另一头才停下,铁头杵在脚边,呼了一口长气。气从嘴里喷出来,在她面前凝成一小团白雾。 +她从那块石头上迈了过去,铁头靴的底沿磕在雪人前爪的指节上,磕得指节上的皮圈咯吱响了一声。雪人的毛抖了一下,没拍下来。她走过去了。她没回头看。她知道如果她回头看,那只前爪会在她后脑勺上拍一下,把她的头连骨带捅进冰里。她一直走到隘口另一头才停下,铁头杵在脚边,呼了一口长气。气从嘴里喷出来,在她面前凝成一小团白雾。 -她赢了,还是她输了?她站在隘口另一头想了很久。风从她身后灌进来,吹得她后颈发凉。Yeti没追上来。她回头看了一眼。Langgud Tradebears The Eviscerated Chill Of Pregnancies还坐在那块石头上,前爪还搭着,没挪窝。它只是坐在那儿,呼出的气一下一下地喷在冰面上。 +她赢了,还是她输了?她站在隘口另一头想了很久。风从她身后灌进来,吹得她后颈发凉。雪人没追上来。她回头看了一眼。朗古德·商熊「剖胎之寒」还坐在那块石头上,前爪还搭着,没挪窝。它只是坐在那儿,呼出的气一下一下地喷在冰面上。 她不打算再退回去了。 她转身往南走,走了几步,又停下。她转回去,走回那块她丢过去的石头边上,蹲下,把石头从冰面上抠起来。石头上的冰被她抠掉一层,露出下面灰白的原色。她把石头搬到隘口正中,竖在路口那儿,竖得稳稳当当。这是凭证。要过的人留在这块石头边上。她没说这是给谁立的规矩,没说这块石头怎么过她才放人过,她只是把石头竖在那儿,转身走了。 -她走回隘口另一头的时候,回头看了一眼。Langgud Tradebears The Eviscerated Chill Of Pregnancies还坐在那块石头上,前爪还搭着,没挪窝。它只是坐在那儿,呼出的气一下一下地喷在冰面上。 +她走回隘口另一头的时候,回头看了一眼。朗古德·商熊「剖胎之寒」还坐在那块石头上,前爪还搭着,没挪窝。它只是坐在那儿,呼出的气一下一下地喷在冰面上。 -隘口那一夜之后过了多久,Ral Fastenhatchets没去算。她只记得再回Fastenhatchets那一带时,山道上的冰已经开始化。她从隘口那头的石块边走过,没停。回去是要带东西的,不是要空手把命交代在那儿。 +隘口那一夜之后过了多久,拉尔·缚斧没去算。她只记得再回缚斧那一带时,山道上的冰已经开始化。她从隘口那头的石块边走过,没停。回去是要带东西的,不是要空手把命交代在那儿。 -Rigoth Stilledearthen是在开春第三周找上来的。 +里戈斯·静土是在开春第三周找上来的。 -他出现在Fastenhatchets南边那条石阶路口的时候,Ral正在跟一个过路的小贩算盐钱。小贩看见这老矮人背着个木匣子从坡上下来,主动让了半步。Rigoth绕过小贩,没看Ral手里那几块粗盐,直接站到她跟前。 +他出现在缚斧南边那条石阶路口的时候,拉尔正在跟一个过路的小贩算盐钱。小贩看见这老矮人背着个木匣子从坡上下来,主动让了半步。里戈斯绕过小贩,没看拉尔手里那几块粗盐,直接站到她跟前。 -“Ral Fastenhatchets。”他说。 +“拉尔·缚斧。”他说。 他没报自己的名字。他把木匣子解下来,搁在两人之间的石阶上。石阶那几块石板被盐卤浸得发白,木匣子搁上去没响。 -“你记不记得Rockjaw那一支还欠我两车铁。”他说。 +“你记不记得拉尔·缚斧那一支还欠我两车铁。”他说。 -“记。”Ral说。 +“记。”拉尔说。 “那账我不要了。” “你要什么。” -Rigoth把木匣子翻开。里头是一本账册,封皮磨得起了毛边,几页纸露在外头,被风掀得一翘一翘的。 +里戈斯把木匣子翻开。里头是一本账册,封皮磨得起了毛边,几页纸露在外头,被风掀得一翘一翘的。 “我替你记。”他说。“每一笔过路钱,每一笔盐,每一笔铁。你不在的时候替你收,你回来了我把账交给你。我不要工钱。” -Ral伸手拨了一下那本账册的封皮。封皮上的字已经认不清了,是上一个主人写的,墨渗进了皮里。她把手缩回来。 +拉尔伸手拨了一下那本账册的封皮。封皮上的字已经认不清了,是上一个主人写的,墨渗进了皮里。她把手缩回来。 “为什么不要工钱。” -“我老了。”Rigoth说。“搬不动铁了。” +“我老了。”里戈斯说。“搬不动铁了。” -Ral看了一眼他的手。这老矮人的手背上青筋鼓得很高,指节却瘦得凹下去,是那种搬了一辈子东西又突然不搬的手。她没点破。 +拉尔看了一眼他的手。这老矮人的手背上青筋鼓得很高,指节却瘦得凹下去,是那种搬了一辈子东西又突然不搬的手。她没点破。 “进来。”她说。 -Rigoth把木匣子合上,抱起,跟在她后头,进了门。 +里戈斯把木匣子合上,抱起,跟在她后头,进了门。 -Rigoth住进来的头一周,Ral只让他在仓房那头坐着。Rigoth把木匣子搁在膝头,账册摊开,谁过路他就抬头看一眼,谁没过来他就低头抄。Ral走过几次,看见他记的和自己心里那笔对得上,没说话。 +里戈斯住进来的头一周,拉尔只让他在仓房那头坐着。里戈斯把木匣子搁在膝头,账册摊开,谁过路他就抬头看一眼,谁没过来他就低头抄。拉尔走过几次,看见他记的和自己心里那笔对得上,没说话。 第二周她把钥匙给了他一把。 “粮仓后门。”她说。“夜里有人敲三下再开。” -Rigoth点头。 +里戈斯点头。 -第三周的时候Ral问了一句:“Fordedwinds那头的市集,这阵子谁去过?” +第三周的时候拉尔问了一句:“涉风渡那头的市集,这阵子谁去过?” -Rigoth翻了翻账册。“没人。”他说。“我记了,没一个Fastenhatchets的去过。” +里戈斯翻了翻账册。“没人。”他说。“我记了,没一个缚斧的去过。” -Ral没接。Rigoth在她背后说了一句: +拉尔没接。里戈斯在她背后说了一句: “我听见说,那头近来来了个鹰人。” -Ral停了一步,没回头。 +拉尔停了一步,没回头。 “鹰人。”她说。 -“嗯。”Rigoth说。“说他不住店,不买货。” +“嗯。”里戈斯说。“说他不住店,不买货。” -Ral这才回过头。 +拉尔这才回过头。 -Fordedwinds的市集开在两块大石之间。Ral去的那个早上天没下雨,页岩上头还有前一晚冻住的薄冰。她一个人去的,斗篷兜帽压低,从东头挤进去。 +涉风渡的市集开在两块大石之间。拉尔去的那个早上天没下雨,页岩上头还有前一晚冻住的薄冰。她一个人去的,斗篷兜帽压低,从东头挤进去。 -她先看见了Momuz Fateddie。 +她先看见了莫穆兹·命终。 -Momuz是她从小的邻居,比她小两岁。Ral离开Fastenhatchets那几年,粮仓就是Momuz替她看着的。Momuz看见Ral,眼里先是一愣,然后笑了一下,从摊子后面绕出来。 +莫穆兹是她从小的邻居,比她小两岁。拉尔离开缚斧那几年,粮仓就是莫穆兹替她看着的。莫穆兹看见拉尔,眼里先是一愣,然后笑了一下,从摊子后面绕出来。 -“你怎么来了。”Momuz说。 +“你怎么来了。”莫穆兹说。 -“路过。”Ral说。 +“路过。”拉尔说。 -Momuz把手上那把秤搁下。秤杆上还挂着一小截麻绳,是刚才称完什么东西没收拢的。她抬手把那截麻绳绕到秤杆头上,动作很熟。Ral看了一眼那个动作,没说话。 +莫穆兹把手上那把秤搁下。秤杆上还挂着一小截麻绳,是刚才称完什么东西没收拢的。她抬手把那截麻绳绕到秤杆头上,动作很熟。拉尔看了一眼那个动作,没说话。 -“我去给你倒碗热的。”Momuz说。 +“我去给你倒碗热的。”莫穆兹说。 -“不用。”Ral说。“你忙。” +“不用。”拉尔说。“你忙。” -Momuz站了一会儿,又回去守她的摊子。Ral挪到了市集东头一个卖皮子的摊子后头,那里有一块半截石墩,正好能坐。她坐下,把斗篷拢紧,目光落在Momuz那摊子前头过路的人身上。 +莫穆兹站了一会儿,又回去守她的摊子。拉尔挪到了市集东头一个卖皮子的摊子后头,那里有一块半截石墩,正好能坐。她坐下,把斗篷拢紧,目光落在莫穆兹那摊子前头过路的人身上。 鹰人是傍晚那阵出现的。 他从市集西头过来,步子不紧不慢。市集里人挤,矮人、人类、几个半大的孩子挤在摊子之间,他一进来就显眼。不是因为他高。是因为他走路不带声响,落地的时候脚尖先点地,然后才把整个脚掌放下来,那是他那族走路的样子。他穿着一件深褐色的短衣,腰上没挂刀,背上一只长弓,弓弦松着。 -Ral看着他。 +拉尔看着他。 -他没去任何一个摊子。他绕过卖皮子的,绕过卖铁器的,绕过卖腌菜的,一直走到Momuz那摊子前。 +他没去任何一个摊子。他绕过卖皮子的,绕过卖铁器的,绕过卖腌菜的,一直走到莫穆兹那摊子前。 -Momuz抬起头。 +莫穆兹抬起头。 -那之后几天,Ral每逢Fordedwinds开市就去,去就坐在那块半截石墩上。她不和Momuz说话,也不和那鹰人说话。 +那之后几天,拉尔每逢涉风渡开市就去,去就坐在那块半截石墩上。她不和莫穆兹说话,也不和那鹰人说话。 -那鹰人叫Guspu Frillyknots,是Rigoth替她打听出来的。Rigoth没进市集,他在市集外头的茶棚子里坐着,谁从里头出来他就跟谁搭两句。第五天他带回这个名字。 +那鹰人叫古斯普·褶结,是里戈斯替她打听出来的。里戈斯没进市集,他在市集外头的茶棚子里坐着,谁从里头出来他就跟谁搭两句。第五天他带回这个名字。 -“Guspu Frillyknots。”Rigoth说。“不是商队的人,也不是哪家请的护卫。他自己一个人。” +“古斯普·褶结。”里戈斯说。“不是商队的人,也不是哪家请的护卫。他自己一个人。” -“他找Momuz做什么。”Ral说。 +“他找莫穆兹做什么。”拉尔说。 -“说话。”Rigoth说。“我隔着问了几个人,都这么说。没见成交过什么。” +“说话。”里戈斯说。“我隔着问了几个人,都这么说。没见成交过什么。” -Ral把这句话在嘴里嚼了嚼。一个不住店不买货的鹰人,跑到市集上,就为了和一个看粮仓的矮女人说话。 +拉尔把这句话在嘴里嚼了嚼。一个不住店不买货的鹰人,跑到市集上,就为了和一个看粮仓的矮女人说话。 -“他说什么。”Ral问。 +“他说什么。”拉尔问。 -Rigoth摇头。“问不出来。Momuz不跟人说。” +里戈斯摇头。“问不出来。莫穆兹不跟人说。” -Ral看了Rigoth一眼。Rigoth把账册合上。 +拉尔看了里戈斯一眼。里戈斯把账册合上。 -“我去盯着。”Rigoth说。 +“我去盯着。”里戈斯说。 -“不用。”Ral说。“你回去把盐账结了。” +“不用。”拉尔说。“你回去把盐账结了。” -Rigoth走后,Ral在屋檐下站了很久。她没再回市集。 +里戈斯走后,拉尔在屋檐下站了很久。她没再回市集。 -再见到Momuz是半个月后。Momuz自己回了一趟Fastenhatchets,说是要清点粮仓后头那几口旧缸。Ral陪她走到后院,看她蹲在缸边用指头敲,敲出空响的就摇一下头。 +再见到莫穆兹是半个月后。莫穆兹自己回了一趟缚斧,说是要清点粮仓后头那几口旧缸。拉尔陪她走到后院,看她蹲在缸边用指头敲,敲出空响的就摇一下头。 -“那头市集。”Ral说。“那个鹰人。” +“那头市集。”拉尔说。“那个鹰人。” -Momuz敲缸的手停了一下。她没抬头。 +莫穆兹敲缸的手停了一下。她没抬头。 -“Guspu。”Momuz说。 +“古斯普。”莫穆兹说。 “嗯。” -“他是我朋友。”Momuz说。 +“他是我朋友。”莫穆兹说。 -Ral没接。Momuz直起腰,把手上的灰在围裙上蹭了两下。 +拉尔没接。莫穆兹直起腰,把手上的灰在围裙上蹭了两下。 -“你问这个做什么。”Momuz说。 +“你问这个做什么。”莫穆兹说。 -“你是我看粮仓的。”Ral说。“那头来了个我不认识的人。” +“你是我看粮仓的。”拉尔说。“那头来了个我不认识的人。” -“我不认识的人多了。”Momuz说。“卖皮子的那个我也不认识。” +“我不认识的人多了。”莫穆兹说。“卖皮子的那个我也不认识。” -Ral没说话。Momuz把缸盖合上,抱起,往仓里走。走到门口她回头说了一句。 +拉尔没说话。莫穆兹把缸盖合上,抱起,往仓里走。走到门口她回头说了一句。 -“Ral。”她说。“我自己的事。” +“拉尔。”她说。“我自己的事。” -Ral点了点头。 +拉尔点了点头。 -Rigoth是冬天头一场雪之后把那句话带回来的。他在仓房后头等Ral,账册翻开在膝头,纸页被风吹得一张一张翻过去,他用手按住。 +里戈斯是冬天头一场雪之后把那句话带回来的。他在仓房后头等拉尔,账册翻开在膝头,纸页被风吹得一张一张翻过去,他用手按住。 “结契了。”他说。 “谁。” -“Guspu Frillyknots和Momuz Fateddie。”Rigoth说。“鹰人那边的契。市集东头那个卖皮子的看见了。” +“古斯普·褶结和莫穆兹·命终。”里戈斯说。“鹰人那边的契。市集东头那个卖皮子的看见了。” -Ral把账册从他手里接过来。她念了一遍那几个字,又念了一遍。 +拉尔把账册从他手里接过来。她念了一遍那几个字,又念了一遍。 -Guspu Frillyknots。Momuz Fateddie。 +古斯普·褶结。莫穆兹·命终。 -她把账册合上,搁回Rigoth膝头。Rigoth看着她,等她说点什么。 +她把账册合上,搁回里戈斯膝头。里戈斯看着她,等她说点什么。 -Ral站了一会儿。 +拉尔站了一会儿。 “她自己的事。”她说。 -Rigoth没再问。 +里戈斯没再问。 -隘口的矮桌是Guspu Frillyknots自己带来的。他把四条腿掰开,桌面放平在两块石墩之间,离Ral守的那条路只差两步。来人过的时候都能看见桌面上铺开的东西:一卷盖满章的羊皮纸,三只小陶碟,碟里是干得发硬的奶酪和一小堆切成方块的熏肉,一壶还没开封的矮麦酒。他把东西一样一样摆出来,摆完便坐到桌后,从腰间抽出一根骨签剔牙。 +隘口的矮桌是古斯普·褶结自己带来的。他把四条腿掰开,桌面放平在两块石墩之间,离拉尔守的那条路只差两步。来人过的时候都能看见桌面上铺开的东西:一卷盖满章的羊皮纸,三只小陶碟,碟里是干得发硬的奶酪和一小堆切成方块的熏肉,一壶还没开封的矮麦酒。他把东西一样一样摆出来,摆完便坐到桌后,从腰间抽出一根骨签剔牙。 -Ral从岗哨那边走过来时,他没抬头。等她在桌对面站定,他才把骨签收起来,拿袍袖擦了一下嘴角,抬眼看她。他眼睛是淡黄的,在冬天的光里显得更浅,瞳孔边上有一圈很细的金线。他先说话,声音从喉咙高处滑下来,滑得很慢,像怕风把它吹散: +拉尔从岗哨那边走过来时,他没抬头。等她在桌对面站定,他才把骨签收起来,拿袍袖擦了一下嘴角,抬眼看她。他眼睛是淡黄的,在冬天的光里显得更浅,瞳孔边上有一圈很细的金线。他先说话,声音从喉咙高处滑下来,滑得很慢,像怕风把它吹散: “你守着一条路,却没有保护者。” -Ral没坐。她站在桌边,左手扶着桌沿,右手还戴着半截皮手套,没脱。那只手指尖发黑,刚从账房那边过来,碰过墨。她没去碰那卷羊皮纸。羊皮纸的封蜡是红的,盖了三枚章,她认得出其中一枚是Ongrun城里某个议事厅的戳,另一枚她没见过。 +拉尔没坐。她站在桌边,左手扶着桌沿,右手还戴着半截皮手套,没脱。那只手指尖发黑,刚从账房那边过来,碰过墨。她没去碰那卷羊皮纸。羊皮纸的封蜡是红的,盖了三枚章,她认得出其中一枚是涉风渡里某个议事厅的戳,另一枚她没见过。 -“我可以让Fordedwinds免受任何骚扰。”Guspu说。他把“骚扰”两个字说得很轻,像说“风”。“只需要你在通行税里分三成给我。三成,不多。我替你挡掉的事,比这三成值钱得多。” +“我可以让涉风渡免受任何骚扰。”古斯普说。他把“骚扰”两个字说得很轻,像说“风”。“只需要你在通行税里分三成给我。三成,不多。我替你挡掉的事,比这三成值钱得多。” -Ral看了一眼那三只陶碟。碟边沿磕掉了一小片,奶酪上落了一点灰。她没碰它们。 +拉尔看了一眼那三只陶碟。碟边沿磕掉了一小片,奶酪上落了一点灰。她没碰它们。 “那三成,”她说,“是给你,还是给你后面的人?” -Guspu笑了一下。那种笑法是从嘴角先动的,眼底不跟。他把骨签又抽出来,在指间转了半圈,又收回去。 +古斯普笑了一下。那种笑法是从嘴角先动的,眼底不跟。他把骨签又抽出来,在指间转了半圈,又收回去。 “你不问,”他说,“我就不说。这是体面。” -Ral把那只皮手套慢慢褪下来,搁在桌沿上。她用空出来的手把那卷羊皮纸推回Guspu那一侧。纸卷在桌面上滚了半圈,撞上陶碟,碟里的熏肉方块震了一下,有一块滑到碟外,落在桌面。 +拉尔把那只皮手套慢慢褪下来,搁在桌沿上。她用空出来的手把那卷羊皮纸推回古斯普那一侧。纸卷在桌面上滚了半圈,撞上陶碟,碟里的熏肉方块震了一下,有一块滑到碟外,落在桌面。 “我买过你的体面吗?”她说。 -Guspu没去扶那块肉。他看着Ral,慢慢把那卷羊皮纸拢回自己这边,卷好,塞回怀里。他没说行,也没说不行。他站起身,把矮麦酒那壶也拎起来,走了。走的时候脚步很轻,靴底像是垫了一层皮。 +古斯普没去扶那块肉。他看着拉尔,慢慢把那卷羊皮纸拢回自己这边,卷好,塞回怀里。他没说行,也没说不行。他站起身,把矮麦酒那壶也拎起来,走了。走的时候脚步很轻,靴底像是垫了一层皮。 那壶酒他没开封,也没留下。 -来试Ral的不止Guspu一个。同一年,Tulon Tongswall也找上门来。Tulon是矮人,身材比Guspu矮半头,肩却很宽,走起路来两侧带风。他没带矮桌,也没带羊皮纸,只带了一个人——他自己的随从,随从手里捧着一只铁匣,匣里是码得整整齐齐的铜锭。 +来试拉尔的不止古斯普一个。同一年,图隆·钳墙也找上门来。图隆是矮人,身材比古斯普矮半头,肩却很宽,走起路来两侧带风。他没带矮桌,也没带羊皮纸,只带了一个人——他自己的随从,随从手里捧着一只铁匣,匣里是码得整整齐齐的铜锭。 -Tulon把Ral堵在隘口的石墙下。他开口比Guspu直白得多。 +图隆把拉尔堵在隘口的石墙下。他开口比古斯普直白得多。 -“三成五。”他说。他站在阴影里,声音从胸腔里压出来,比Guspu那种滑下来的声调重得多。“我替你拦下来的人,比那位爷能叫来的多。价钱也公道。” +“三成五。”他说。他站在阴影里,声音从胸腔里压出来,比古斯普那种滑下来的声调重得多。“我替你拦下来的人,比那位爷能叫来的多。价钱也公道。” -他身后那个随从把铁匣盖打开,让Ral看。铜锭在阴天的光里发暗,颜色像干了的血。 +他身后那个随从把铁匣盖打开,让拉尔看。铜锭在阴天的光里发暗,颜色像干了的血。 -Ral没看那只铁匣。她看的是Tulon的靴子。靴面上有泥,泥是红的,从隘口外的坡道上带回来的。她认得那种土。 +拉尔没看那只铁匣。她看的是图隆的靴子。靴面上有泥,泥是红的,从隘口外的坡道上带回来的。她认得那种土。 “这三成五,”她说,“是给我,还是给你后面那一串?” -Tulon的脸动了一下。他没笑。他把铁匣盖合上,示意随从退后一步。 +图隆的脸动了一下。他没笑。他把铁匣盖合上,示意随从退后一步。 “你要是问这个,”他说,“我就没法跟你谈。” -“那就别谈。”Ral说。她转身往岗哨那边走。走到墙根时,她听见Tulon在身后补了一句,声音还是那种压得很低的腔调: +“那就别谈。”拉尔说。她转身往岗哨那边走。走到墙根时,她听见图隆在身后补了一句,声音还是那种压得很低的腔调: “下次来,可就不是铜了。” -Ral没回头。她回到岗哨屋里,把门掩上,在桌前站了一会儿。桌上摊着她自己的账册,账册里记的是这一个月的通行数和税。她把Tulon的名字写进另一本册子的封皮内侧,写完又划掉,重新写。划掉的那道墨痕她没擦,留着。 +拉尔没回头。她回到岗哨屋里,把门掩上,在桌前站了一会儿。桌上摊着她自己的账册,账册里记的是这一个月的通行数和税。她把图隆的名字写进另一本册子的封皮内侧,写完又划掉,重新写。划掉的那道墨痕她没擦,留着。 -之后她让人把Rigoth叫来。 +之后她让人把里戈斯叫来。 -Rigoth来的时候天还没全黑,岗哨屋里的油灯点了一盏,火苗缩在灯芯上,一跳一跳的。Ral把两只册子都推到他面前。 +里戈斯来的时候天还没全黑,岗哨屋里的油灯点了一盏,火苗缩在灯芯上,一跳一跳的。拉尔把两只册子都推到他面前。 “以后,”她说,“凡是有外头的人来找我,不论开口的是谁,手里拿的是纸、是铜、还是别的,你都给我记下来。找我的时辰,在哪找的,带了什么,说了什么,一句都不许漏。” -Rigoth把册子翻开,看了一眼第一页。他没问为什么。他把墨瓶推到自己这边,又从怀里摸出一支秃头的鹅毛笔。 +里戈斯把册子翻开,看了一眼第一页。他没问为什么。他把墨瓶推到自己这边,又从怀里摸出一支秃头的鹅毛笔。 “连威胁也记?”他问。 -“连威胁也记。”Ral说。 +“连威胁也记。”拉尔说。 -Rigoth点了点头,低头在第一页顶上写了日期,写完停了一下,又在日期下头加了三个小字:Guspu,Tulon。他写完把笔搁下,抬头看Ral。 +里戈斯点了点头,低头在第一页顶上写了日期,写完停了一下,又在日期下头加了三个小字:古斯普,图隆。他写完把笔搁下,抬头看拉尔。 -Ral站在灯边。她脸上没多余的表情,眼底那点东西也压得很平。她看着Rigoth手里那支秃笔,看了一会儿,说: +拉尔站在灯边。她脸上没多余的表情,眼底那点东西也压得很平。她看着里戈斯手里那支秃笔,看了一会儿,说: “我不信他们是单独来的。” -Rigoth没接话。他把册子合上,夹在腋下,站起身往外走。走到门口他停了一下,回头: +里戈斯没接话。他把册子合上,夹在腋下,站起身往外走。走到门口他停了一下,回头: -“那Falcon那边呢?” +“那隼族那边呢?” -Falcon那边指的是她自己这一族的议事。Ral把手套重新戴上,拉了拉指根。 +隼族那边指的是她自己这一族的议事。拉尔把手套重新戴上,拉了拉指根。 “先记,”她说,“先别送过去。等他们自己来问。” -Rigoth“嗯”了一声,出了门。门在风里晃了两下,最后贴上门框,把那点灯光夹在屋里,没让它漏出去。 +里戈斯“嗯”了一声,出了门。门在风里晃了两下,最后贴上门框,把那点灯光夹在屋里,没让它漏出去。 194年的冬天比往年早。 -Ral Fastenhatchets揣着账册往本家议事堂走的时候,巷子里的冻土还在前一年的积雪下面硬着,踩上去鞋底能听见碎响。她没穿厚衣服,矮个子在风里走快了反而不冷,鼻尖和耳廓冻得发木。账册是本家这些年的进出,从The Volcano Of Ravens分出来的Fordedwinds每一笔都记在上头。她要的不是议事堂,是议事堂后头那道矮门,矮门里头连着鹰人审判庭。鹰人不审本家的人,但账册上的事能定罪,定罪了本家才能动。 +拉尔·缚斧揣着账册往本家议事堂走的时候,巷子里的冻土还在前一年的积雪下面硬着,踩上去鞋底能听见碎响。她没穿厚衣服,矮个子在风里走快了反而不冷,鼻尖和耳廓冻得发木。账册是本家这些年的进出,从渡鸦火山分出来的涉风渡每一笔都记在上头。她要的不是议事堂,是议事堂后头那道矮门,矮门里头连着鹰人审判庭。鹰人不审本家的人,但账册上的事能定罪,定罪了本家才能动。 -矮门前站着两个鹰人,看了她一眼,没拦。Ral把账册递过去,说:“请把这份呈给审判庭。立案的话,被告是Guspu Frillyknots,罪名是他试图收买Fordedwinds的守门人。”她停了一下,又说:“这里记了每一次。” +矮门前站着两个鹰人,看了她一眼,没拦。拉尔把账册递过去,说:“请把这份呈给审判庭。立案的话,被告是古斯普·褶结,罪名是他试图收买涉风渡的守门人。”她停了一下,又说:“这里记了每一次。” -审判庭不大,木头的长椅,旧挂毯。Ral坐在证人席的椅子上,椅背硬,靠上去肩胛骨硌得慌。她没靠实,只挨着椅子边坐。Guspu Frillyknots被两个鹰人架着带进来。他没戴枷,矮凳上坐下,手搁在腿边,看了她一眼。Ral没避开。她把账册里自己圈出来的几页递给主审的鹰人,说:“第一页是他许给守门人的东西,第五页是守门人交回来的东西,第十一页是他第二次让人转交给我的话。”主审翻到第十一页,问:“这是你的笔迹?”Ral说:“是他让人转交的。我没回。”主审又问:“你为什么记下来?”Ral说:“因为他不只做了一次。” +审判庭不大,木头的长椅,旧挂毯。拉尔坐在证人席的椅子上,椅背硬,靠上去肩胛骨硌得慌。她没靠实,只挨着椅子边坐。古斯普·褶结被两个鹰人架着带进来。他没戴枷,矮凳上坐下,手搁在腿边,看了她一眼。拉尔没避开。她把账册里自己圈出来的几页递给主审的鹰人,说:“第一页是他许给守门人的东西,第五页是守门人交回来的东西,第十一页是他第二次让人转交给我的话。”主审翻到第十一页,问:“这是你的笔迹?”拉尔说:“是他让人转交的。我没回。”主审又问:“你为什么记下来?”拉尔说:“因为他不只做了一次。” -判决很快。Guspu Frillyknots构陷守门人成立。鹰人把Guspu往门口带,门还没关,门被人从外头撞开,Momuz冲进来。 +判决很快。古斯普·褶结构陷守门人成立。鹰人把古斯普往门口带,门还没关,门被人从外头撞开,莫穆兹冲进来。 -Momuz比Ral高半头,冲进来的时候差点撞上带人的鹰人。她退了一步,绕过鹰人,冲Ral喊:“你为什么不先跟我说?”声音在审判庭里撞了几个来回,比平常高出许多。 +莫穆兹比拉尔高半头,冲进来的时候差点撞上带人的鹰人。她退了一步,绕过鹰人,冲拉尔喊:“你为什么不先跟我说?”声音在审判庭里撞了几个来回,比平常高出许多。 -Ral从证人席上下来,看了看Momuz,看了看门口的鹰人,又看了看被架着的Guspu。她走近Momuz一步,说:“你早替他说话了。” +拉尔从证人席上下来,看了看莫穆兹,看了看门口的鹰人,又看了看被架着的古斯普。她走近莫穆兹一步,说:“你早替他说话了。” -Momuz的手抬起来,又放下。她看了看Ral,看了看门口的Guspu,没再说话,转身就往门外走。走到门口停了一下,没回头,又接着走。门在她身后合上,木头碰木头,沉闷的一声。 +莫穆兹的手抬起来,又放下。她看了看拉尔,看了看门口的古斯普,没再说话,转身就往门外走。走到门口停了一下,没回头,又接着走。门在她身后合上,木头碰木头,沉闷的一声。 -Ral站在审判庭里,看着合上的门。她知道这门一关,她们十几年的交情从今天起就变了。往外走的时候手还扶着账册的封皮,封皮上有茶渍,那是Momuz前天坐她家喝茶时洒的。她把账册收进袖筒里,没擦。 +拉尔站在审判庭里,看着合上的门。她知道这门一关,她们十几年的交情从今天起就变了。往外走的时候手还扶着账册的封皮,封皮上有茶渍,那是莫穆兹前天坐她家喝茶时洒的。她把账册收进袖筒里,没擦。 她以为定罪能结束这一切。 -Guspu Frillyknots在审判庭关了没几天就被放了出来。Ral是从Fordedwinds守门人那里听说的。她没去问为什么。第二天本家议事里她提了一句:“Guspu Frillyknots回了Fordedwinds。”没人答。议事散了,她一个人坐了一会儿,把账册里Guspu那一页折了个角。 +古斯普·褶结在审判庭关了没几天就被放了出来。拉尔是从涉风渡守门人那里听说的。她没去问为什么。第二天本家议事里她提了一句:“古斯普·褶结回了涉风渡。”没人答。议事散了,她一个人坐了一会儿,把账册里古斯普那一页折了个角。 -195年开春,Fordedwinds的守门人又来找她。守门人是本家的老人,比Ral大四十岁,没进Ral的屋,站在门口说:“Guspu Frillyknots又让人送东西来了。是Momuz送的。一个箱子,还有口信。”Ral问:“口信说什么?”守门人说:“让你‘先收一笔’。”Ral说:“箱子你收着,我不进门。” +195年开春,涉风渡的守门人又来找她。守门人是本家的老人,比拉尔大四十岁,没进拉尔的屋,站在门口说:“古斯普·褶结又让人送东西来了。是莫穆兹送的。一个箱子,还有口信。”拉尔问:“口信说什么?”守门人说:“让你‘先收一笔’。”拉尔说:“箱子你收着,我不进门。” -守门人走了。她关上门,背靠着门站了一会儿。箱子里的东西她不看,Guspu让人转交的东西她从来不看。她知道里头是什么,知道里头是什么的时候,看不看都一样。 +守门人走了。她关上门,背靠着门站了一会儿。箱子里的东西她不看,古斯普让人转交的东西她从来不看。她知道里头是什么,知道里头是什么的时候,看不看都一样。 -Momuz那天晚上来找她。 +莫穆兹那天晚上来找她。 -Momuz进Ral的屋,没坐,站在桌边,把Guspu给她的箱子又提了过来。箱子不大,盖子是木头的,没上锁。Momuz把箱子往Ral这一侧推了推,说:“他让我带给你的。”Ral没看箱子。她抬头看Momuz的脸。Momuz的脸比白天更白,下巴绷着,嘴唇干。Ral说:“你转告他,他越这样,我越不会松手。” +莫穆兹进拉尔的屋,没坐,站在桌边,把古斯普给她的箱子又提了过来。箱子不大,盖子是木头的,没上锁。莫穆兹把箱子往拉尔这一侧推了推,说:“他让我带给你的。”拉尔没看箱子。她抬头看莫穆兹的脸。莫穆兹的脸比白天更白,下巴绷着,嘴唇干。拉尔说:“你转告他,他越这样,我越不会松手。” -Momuz的手从箱子上挪开,搁到自己腿上。她低着头,看着自己搁在腿上的手,看了很久,然后说:“他救过我弟弟的命。我还不掉。” +莫穆兹的手从箱子上挪开,搁到自己腿上。她低着头,看着自己搁在腿上的手,看了很久,然后说:“他救过我弟弟的命。我还不掉。” -Ral的嘴张了一下,又合上。她看着Momuz肩塌着、下巴抵着锁骨的样子,知道Momuz没骗她。Guspu Frillyknots那年从流民里把Momuz的弟弟救出来是真的,Momuz记了十几年也是真的。她以前只知道Guspu用钱砸她,现在才知道Guspu用别的东西砸Momuz。 +拉尔的嘴张了一下,又合上。她看着莫穆兹肩塌着、下巴抵着锁骨的样子,知道莫穆兹没骗她。古斯普·褶结那年从流民里把莫穆兹的弟弟救出来是真的,莫穆兹记了十几年也是真的。她以前只知道古斯普用钱砸她,现在才知道古斯普用别的东西砸莫穆兹。 -Momuz没等她答,提起箱子就往外走。Ral跟着走到门口,看着Momuz的背影穿过巷子。Momuz走得不快,背影被巷口的灯拉得很长,又被巷子收短。Momuz走远,她关了门。 +莫穆兹没等她答,提起箱子就往外走。拉尔跟着走到门口,看着莫穆兹的背影穿过巷子。莫穆兹走得不快,背影被巷口的灯拉得很长,又被巷子收短。莫穆兹走远,她关了门。 -她第一次动摇,不是因为钱,是因为Momuz低头的样子。关了门,没点灯,在黑里站了一会儿,又把门打开,让灯透进来。她站在门里,把账册里有关Momuz弟弟那一页折了个角,又把角抹平。她不记,又想折好。最后把账册搁在桌上,没动。 +她第一次动摇,不是因为钱,是因为莫穆兹低头的样子。关了门,没点灯,在黑里站了一会儿,又把门打开,让灯透进来。她站在门里,把账册里有关莫穆兹弟弟那一页折了个角,又把角抹平。她不记,又想折好。最后把账册搁在桌上,没动。 -Tulon Tongswall那年也来过一次。Tulon是本家的另一房,比Ral小一辈,平时不来Fordedwinds。那天他来,是替Guspu Frillyknots送东西。Ral在议事堂后头的过道里截住他,问:“你来做什么?”Tulon说:“给Guspu叔送点东西。”Ral说:“这里不收Guspu Frillyknots的东西。”Tulon看了她一眼,没说话,提着东西出了议事堂。 +图隆·钳墙那年也来过一次。图隆是本家的另一房,比拉尔小一辈,平时不来涉风渡。那天他来,是替古斯普·褶结送东西。拉尔在议事堂后头的过道里截住他,问:“你来做什么?”图隆说:“给古斯普叔送点东西。”拉尔说:“这里不收古斯普·褶结的东西。”图隆看了她一眼,没说话,提着东西出了议事堂。 -Ral站在过道里,看着Tulon走出去,没去拦。站到腿酸,才回自己的屋。 +拉尔站在过道里,看着图隆走出去,没去拦。站到腿酸,才回自己的屋。 -那年冬天还冷。Fordedwinds外头的河道冻了一层薄冰,议事堂侧门一推开,冷得人眼睛发涩。Ral坐在桌前,桌角搁着昨天没合上的账册。Rigoth从外头进来,靴子上带着泥,雪水还没干透,把一只陶碗放在她面前。碗里是热的,冒出一股焦味。 +那年冬天还冷。涉风渡外头的河道冻了一层薄冰,议事堂侧门一推开,冷得人眼睛发涩。拉尔坐在桌前,桌角搁着昨天没合上的账册。里戈斯从外头进来,靴子上带着泥,雪水还没干透,把一只陶碗放在她面前。碗里是热的,冒出一股焦味。 -Rigoth说:“他们又派Tulon来了。” +里戈斯说:“他们又派图隆来了。” -Ral没抬头。她把账册翻到上个月那一页,看见自己用炭条画的那道杠还在,杠下面空白。Rigoth又说:“在议事堂外头,我没让他进来。”Ral嗯了一声,把账册合上,搁在桌角。Rigoth站着,等她开口。 +拉尔没抬头。她把账册翻到上个月那一页,看见自己用炭条画的那道杠还在,杠下面空白。里戈斯又说:“在议事堂外头,我没让他进来。”拉尔嗯了一声,把账册合上,搁在桌角。里戈斯站着,等她开口。 -Ral说:“他几时到的?” +拉尔说:“他几时到的?” -“天没亮。”Rigoth说,“他带了一只木匣,匣上没封,里头是一块布包着的东西。我没让他打开。” +“天没亮。”里戈斯说,“他带了一只木匣,匣上没封,里头是一块布包着的东西。我没让他打开。” -Ral这才抬头。她看着Rigoth的脸,看见她丈夫下颌骨的棱角比去年更瘦。Rigoth又说:“我让他在门外等着。他站了一刻钟,自己走了。匣子没留下,搁在台阶上。我把它搬进库房了,没打开。” +拉尔这才抬头。她看着里戈斯的脸,看见她丈夫下颌骨的棱角比去年更瘦。里戈斯又说:“我让他在门外等着。他站了一刻钟,自己走了。匣子没留下,搁在台阶上。我把它搬进库房了,没打开。” -Ral把账册又翻开,摊在桌上。她从桌边那只小木盒里取出一根炭条,在空白处写下今天的日期,又在日期下面写:Tulon Tongswall,晨,议事堂外,未入。写完,她把炭条搁回盒里。 +拉尔把账册又翻开,摊在桌上。她从桌边那只小木盒里取出一根炭条,在空白处写下今天的日期,又在日期下面写:图隆·钳墙,晨,议事堂外,未入。写完,她把炭条搁回盒里。 -Rigoth说:“要不要我去库房看看那块布?” +里戈斯说:“要不要我去库房看看那块布?” -“不要。”Ral说,“先搁着。” +“不要。”拉尔说,“先搁着。” -Rigoth站在那里,又等了一会儿。Ral把账册合上,搁在桌角,站起来,走到门边,把门推开一线。冷风灌进来,吹得桌上那根刚搁下的炭条滚了两寸。Rigoth走过去,把炭条拾起来,放回盒里。 +里戈斯站在那里,又等了一会儿。拉尔把账册合上,搁在桌角,站起来,走到门边,把门推开一线。冷风灌进来,吹得桌上那根刚搁下的炭条滚了两寸。里戈斯走过去,把炭条拾起来,放回盒里。 -Ral站在门边,背对着Rigoth,说:“他们要把我拖到没人信我的那天。” +拉尔站在门边,背对着里戈斯,说:“他们要把我拖到没人信我的那天。” -Rigoth没说话。他把账册从桌角拿起来,搁到柜子里,把柜门合上。他问:“你还要记吗?” +里戈斯没说话。他把账册从桌角拿起来,搁到柜子里,把柜门合上。他问:“你还要记吗?” -“记。”Ral说,“记到他们不敢再来,或者我不在了。” +“记。”拉尔说,“记到他们不敢再来,或者我不在了。” -Rigoth没接话。他走到门边,把门关上,把门闩落下来。屋子里一下子暗下来,只有桌上那盏油灯还亮着。Ral转过身,看着那盏灯。Rigoth说:“我去库房看一眼。”Ral点点头。Rigoth开门出去,把门带上,靴子踩在雪地上,声音一下一下远了。 +里戈斯没接话。他走到门边,把门关上,把门闩落下来。屋子里一下子暗下来,只有桌上那盏油灯还亮着。拉尔转过身,看着那盏灯。里戈斯说:“我去库房看一眼。”拉尔点点头。里戈斯开门出去,把门带上,靴子踩在雪地上,声音一下一下远了。 -Ral站在门里,听见脚步声拐过屋角,听不见了。她把柜门打开,把账册取出来,翻到今天那一页,又看了一遍。她在Tulon那一行下面加了一句话:木匣未封,布包,未启。写完,她把账册合上,搁回柜里。 +拉尔站在门里,听见脚步声拐过屋角,听不见了。她把柜门打开,把账册取出来,翻到今天那一页,又看了一遍。她在图隆那一行下面加了一句话:木匣未封,布包,未启。写完,她把账册合上,搁回柜里。 -Rigoth回来的时候,Ral已经坐在桌前,手里捏着一只空碗。Rigoth说:“布包里是一块铁印,印上刻的是Guspu Frillyknots的徽。”Ral没说话。Rigoth又说:“印背刻了一行小字,认不全,只认得‘Fordedwinds’和‘三成’。” +里戈斯回来的时候,拉尔已经坐在桌前,手里捏着一只空碗。里戈斯说:“布包里是一块铁印,印上刻的是古斯普·褶结的徽。”拉尔没说话。里戈斯又说:“印背刻了一行小字,认不全,只认得‘涉风渡’和‘三成’。” -Ral把空碗搁在桌上,说:“收起来。”Rigoth说:“收到哪里?”Ral说:“收到库房最里头那口箱子里,箱子压上去年那批铁。”Rigoth点点头,又出去了一趟。Ral坐在桌前,听见他开库房门,听见铁块挪动的声音,听见他回来,把库房门锁上。 +拉尔把空碗搁在桌上,说:“收起来。”里戈斯说:“收到哪里?”拉尔说:“收到库房最里头那口箱子里,箱子压上去年那批铁。”里戈斯点点头,又出去了一趟。拉尔坐在桌前,听见他开库房门,听见铁块挪动的声音,听见他回来,把库房门锁上。 -那年冬天剩下的日子,Ral每天早起,第一件事是翻开账册,在当天那一行写下日期,再把昨天的事补完。Tulon没再来。Rigoth每天清早扫台阶,把台阶上的脚印扫掉。 +那年冬天剩下的日子,拉尔每天早起,第一件事是翻开账册,在当天那一行写下日期,再把昨天的事补完。图隆没再来。里戈斯每天清早扫台阶,把台阶上的脚印扫掉。 -到了第二年开春,Fordedwinds外头的冰化了,河道又开始流。Ral那天在议事堂后头的过道里截住一个人。那人比Ral高一个头,肩上披着一件灰布,灰布下露出一截细长的嘴,嘴尖拱起,像个小铲。那人见Ral挡在路中间,停下脚步。 +到了第二年开春,涉风渡外头的冰化了,河道又开始流。拉尔那天在议事堂后头的过道里截住一个人。那人比拉尔高一个头,肩上披着一件灰布,灰布下露出一截细长的嘴,嘴尖拱起,像个小铲。那人见拉尔挡在路中间,停下脚步。 -Ral说:“Astri Flayerline。” +拉尔说:“阿斯特里·剥血。” -Astri Flayerline点点头,说:“Ral Fastenhatchets。”Ral说:“你来做什么?”Astri Flayerline说:“替Guspu Frillyknots问一句话。”Ral问:“哪一句?”Astri Flayerline说:“你肯不肯收那三成。” +阿斯特里·剥血点点头,说:“拉尔·缚斧。”拉尔说:“你来做什么?”阿斯特里·剥血说:“替古斯普·褶结问一句话。”拉尔问:“哪一句?”阿斯特里·剥血说:“你肯不肯收那三成。” -Ral靠着墙,手背在身后摸着墙缝里那块石头。那块石头是早年搬到路口的,棱角早磨没了,圆圆的一块,搁在墙缝里,正好填住那道缝。她摸到石头凸起的那一面,手指停下来。 +拉尔靠着墙,手背在身后摸着墙缝里那块石头。那块石头是早年搬到路口的,棱角早磨没了,圆圆的一块,搁在墙缝里,正好填住那道缝。她摸到石头凸起的那一面,手指停下来。 -她说:“你回去告诉Guspu Frillyknots,他那块铁印还在我库房里。” +她说:“你回去告诉古斯普·褶结,他那块铁印还在我库房里。” -Astri Flayerline没说话。他看了她一眼,又看了一眼她身后那道墙缝。Ral说:“他还带什么话来?” +阿斯特里·剥血没说话。他看了她一眼,又看了一眼她身后那道墙缝。拉尔说:“他还带什么话来?” -Astri Flayerline说:“他说,下一个被定罪的是你。” +阿斯特里·剥血说:“他说,下一个被定罪的是你。” -Ral笑了。她松开手,从墙缝里抽出那块石头,搁在地上。石头落在过道的石板上,响了一声。她弯腰把石头拾起来,又塞回墙缝。石头比她手心凉。 +拉尔笑了。她松开手,从墙缝里抽出那块石头,搁在地上。石头落在过道的石板上,响了一声。她弯腰把石头拾起来,又塞回墙缝。石头比她手心凉。 -她说:“Rigoth。” +她说:“里戈斯。” -Rigoth从过道另一头走过来。他手里拿着一本账册,账册是新换的,封皮上还沾着木屑。他看了Astri Flayerline一眼,没说话。Ral说:“把Astri也记上去。” +里戈斯从过道另一头走过来。他手里拿着一本账册,账册是新换的,封皮上还沾着木屑。他看了阿斯特里·剥血一眼,没说话。拉尔说:“把阿斯特里也记上去。” -Rigoth把账册翻开,翻到新的一页。他从腰间抽出一根炭条,在新一页上写下日期,又在日期下面写:Astri Flayerline,春,过道,替Guspu Frillyknots问三成。写完,他把炭条递回腰间,把账册合上,搁在腋下。 +里戈斯把账册翻开,翻到新的一页。他从腰间抽出一根炭条,在新一页上写下日期,又在日期下面写:阿斯特里·剥血,春,过道,替古斯普·褶结问三成。写完,他把炭条递回腰间,把账册合上,搁在腋下。 -Astri Flayerline站在过道里,看了Ral一眼,又看了一眼Rigoth腋下那本账册。Ral说:“你走的时候,从议事堂正门出,不要走后头的门。”Astri Flayerline没接话,转身往议事堂正门方向走。Ral看着他走远,背影拐过墙角,看不见了。 +阿斯特里·剥血站在过道里,看了拉尔一眼,又看了一眼里戈斯腋下那本账册。拉尔说:“你走的时候,从议事堂正门出,不要走后头的门。”阿斯特里·剥血没接话,转身往议事堂正门方向走。拉尔看着他走远,背影拐过墙角,看不见了。 -Ral蹲下来,把墙缝里那块石头又摸了一遍。石头比她手心凉,凉得手心发麻。她把手抽出来,在裤腿上蹭了两下,站起来。 +拉尔蹲下来,把墙缝里那块石头又摸了一遍。石头比她手心凉,凉得手心发麻。她把手抽出来,在裤腿上蹭了两下,站起来。 -Rigoth说:“回去?” +里戈斯说:“回去?” -Ral说:“等会儿。” +拉尔说:“等会儿。” 她站在墙缝前,看着那块石头。去年冬天,石头边上落了一层薄雪,雪水化进墙缝里,缝里的土比别处黑。今年开春,雪化得早,墙缝里的土干了,颜色比墙外头的石板浅。她伸手在石头上按了一下,石头没动,还是卡在缝里。 -Rigoth说:“还磨?” +里戈斯说:“还磨?” -Ral说:“不磨。”她把手收回来,转身往议事堂走。Rigoth跟在她后头,手里还夹着那本账册。过道里的风比外头暖,带着议事堂里头烧水的气味。 +拉尔说:“不磨。”她把手收回来,转身往议事堂走。里戈斯跟在她后头,手里还夹着那本账册。过道里的风比外头暖,带着议事堂里头烧水的气味。 -Ral走到议事堂门口,没进去,转身对Rigoth说:“今天的事,回去补上。”Rigoth点点头,把账册从腋下取出来,翻开,又在Astri那一行下面加了一句:又言,下一个被定罪的是她。写完,他把账册合上。 +拉尔走到议事堂门口,没进去,转身对里戈斯说:“今天的事,回去补上。”里戈斯点点头,把账册从腋下取出来,翻开,又在阿斯特里那一行下面加了一句:又言,下一个被定罪的是她。写完,他把账册合上。 -Ral说:“走。” +拉尔说:“走。” 两个人往回走。过道拐角处,墙上那块石头还卡在缝里,没掉下来。石头边上有一道她刚按出来的手印,手印比石头凉。 diff --git a/output/volumes/v1/chapters/001-181-198.md b/output/volumes/v1/chapters/001-181-198.md index bcfdef6..2ec9f2f 100644 --- a/output/volumes/v1/chapters/001-181-198.md +++ b/output/volumes/v1/chapters/001-181-198.md @@ -1,39 +1,39 @@ # 守门人 -181年的Fordedwinds还没有名字。Ral Fastenhatchets站在那条冻硬的隘口,面前是Langgud Tradebears The Eviscerated Chill Of Pregnancies——一个Yeti,比她高两倍,呼出的气能把胡子结冰。她本可以退回矿洞,但她留了下来。两次照面之后,Langgud再也没出现在Fordedwinds,Ral也不确定自己是赢了,还是对方改了主意。她只做了一件事:把一块石头搬到路口,当作凭证——要过Fordedwinds,先问她。 +181年的涉风渡还没有名字。拉尔·缚斧站在那条冻硬的隘口,面前是朗古德·商熊「剖胎之寒」——一个雪人,比她高两倍,呼出的气能把胡子结冰。她本可以退回矿洞,但她留了下来。两次照面之后,朗古德再也没出现在涉风渡,拉尔也不确定自己是赢了,还是对方改了主意。她只做了一件事:把一块石头搬到路口,当作凭证——要过涉风渡,先问她。 -从那一刻起,她的目标就写得很清楚:Fordedwinds不做任何人的附庸。她卖通行权,但只卖一次,绝不签卖身契。 +从那一刻起,她的目标就写得很清楚:涉风渡不做任何人的附庸。她卖通行权,但只卖一次,绝不签卖身契。 -188年,Rigoth Stilledearthen来投奔她。这老矮人带着一本账册,说愿意替她记下每一笔过路钱。Ral收留了他。同年,一个鹰人出现在Fordedwinds的市场上。Guspu Frillyknots。他不住店,不买货,只和Momuz Fateddie说话。Momuz是Ral从小的邻居,替她管着粮仓。Ral远远看着,没有上前。她后来对Rigoth说:“去查查那只鹰为什么总找Momuz。” +188年,里戈斯·静土来投奔她。这老矮人带着一本账册,说愿意替她记下每一笔过路钱。拉尔收留了他。同年,一个鹰人出现在涉风渡的市场上。古斯普·褶结。他不住店,不买货,只和莫穆兹·命终说话。莫穆兹是拉尔从小的邻居,替她管着粮仓。拉尔远远看着,没有上前。她后来对里戈斯说:“去查查那只鹰为什么总找莫穆兹。” -Rigoth没查出结果,只记下一条:Guspu Frillyknots与Momuz Fateddie结了契。Ral把这句话念了两遍,最后只说:“她自己的事。” +里戈斯没查出结果,只记下一条:古斯普·褶结与莫穆兹·命终结了契。拉尔把这句话念了两遍,最后只说:“她自己的事。” -193年,Guspu第一次找上Ral。他在隘口摆了一张矮桌,拿着一卷盖满章的羊皮纸。他说话的声音像从高处滑下来:“你守着一条路,却没有保护者。我可以让Fordedwinds免受任何骚扰,只需要你在通行税里分三成给我。” +193年,古斯普第一次找上拉尔。他在隘口摆了一张矮桌,拿着一卷盖满章的羊皮纸。他说话的声音像从高处滑下来:“你守着一条路,却没有保护者。我可以让涉风渡免受任何骚扰,只需要你在通行税里分三成给我。” -Ral没碰那卷纸。她问他:“那三成,是给你,还是给你后面的人?” +拉尔没碰那卷纸。她问他:“那三成,是给你,还是给你后面的人?” -Guspu笑了:“你不问,我就不说。这是体面。” +古斯普笑了:“你不问,我就不说。这是体面。” -Ral把羊皮纸推回去:“我买过你的体面吗?” +拉尔把羊皮纸推回去:“我买过你的体面吗?” -同年Tulon Tongswall也来试探,开价更直白。Ral同样拒绝。她开始让Rigoth把每一次贿赂、每一次威胁都记下来。她不信这些人是单独来的。 +同年图隆·钳墙也来试探,开价更直白。拉尔同样拒绝。她开始让里戈斯把每一次贿赂、每一次威胁都记下来。她不信这些人是单独来的。 -194年,Ral把账册送到The Volcano Of Ravens。她不是去求公正,是去逼他们立案。她在审判庭上只说了两句:一句是“Guspu Frillyknots试图收买Fordedwinds的守门人”,另一句是“这里记了每一次”。Guspu被定罪。鹰人被带走时,Momuz冲进审判庭,冲Ral喊:“你为什么不先跟我说?” +194年,拉尔把账册送到渡鸦火山。她不是去求公正,是去逼他们立案。她在审判庭上只说了两句:一句是“古斯普·褶结试图收买涉风渡的守门人”,另一句是“这里记了每一次”。古斯普被定罪。鹰人被带走时,莫穆兹冲进审判庭,冲拉尔喊:“你为什么不先跟我说?” -Ral看着朋友:“你早替他说话了。” +拉尔看着朋友:“你早替他说话了。” -Momuz没再说话。她们十几年的交情从那天起裂了。 +莫穆兹没再说话。她们十几年的交情从那天起裂了。 -Ral以为定罪能结束这一切。她错了。 +拉尔以为定罪能结束这一切。她错了。 -195年,Guspu虽然被定罪,人却没被关多久。他回到Fordedwinds,不再亲自出面,改为让Momuz转交口信和箱子。箱子里的东西Ral从来不看。她对Momuz说:“你转告他,他越这样,我越不会松手。”Momuz低着头说:“他救过我弟弟的命。我还不掉。”Ral第一次动摇,不是因为钱,而是因为朋友被夹在中间。 +195年,古斯普虽然被定罪,人却没被关多久。他回到涉风渡,不再亲自出面,改为让莫穆兹转交口信和箱子。箱子里的东西拉尔从来不看。她对莫穆兹说:“你转告他,他越这样,我越不会松手。”莫穆兹低着头说:“他救过我弟弟的命。我还不掉。”拉尔第一次动摇,不是因为钱,而是因为朋友被夹在中间。 -197年,Tulon又来了,像闻到伤口的狼。Ral在夜里对Rigoth说:“他们要把我拖到没人信我的那天。”Rigoth合上账册,只问了一句:“你还要记吗?” +197年,图隆又来了,像闻到伤口的狼。拉尔在夜里对里戈斯说:“他们要把我拖到没人信我的那天。”里戈斯合上账册,只问了一句:“你还要记吗?” “记。”她说,“记到他们不敢再来,或者我不在了。” -198年,Astri Flayerline出现在同样的路口,带着同样的问题,只是多了一点新东西:他不仅出价,还威胁说,如果Ral不合作,下一个被定罪的就是她。Ral笑了。她第一次意识到,真正的转折不在194年的定罪,而在于她终于明白:Guspu要的不是那三成税,而是让她也欠他,让她低头。她偏不。 +198年,阿斯特里·剥血出现在同样的路口,带着同样的问题,只是多了一点新东西:他不仅出价,还威胁说,如果拉尔不合作,下一个被定罪的就是她。拉尔笑了。她第一次意识到,真正的转折不在194年的定罪,而在于她终于明白:古斯普要的不是那三成税,而是让她也欠他,让她低头。她偏不。 -她站在那块当年搬到路口的石头边,对Rigoth说:“把Astri也记上去。” +她站在那块当年搬到路口的石头边,对里戈斯说:“把阿斯特里也记上去。” -Rigoth翻开新的一页。石头上落了一层薄雪。 +里戈斯翻开新的一页。石头上落了一层薄雪。 diff --git a/output/volumes/v1/chapters/002-202-216.md b/output/volumes/v1/chapters/002-202-216.md index cd87600..f7ccf39 100644 --- a/output/volumes/v1/chapters/002-202-216.md +++ b/output/volumes/v1/chapters/002-202-216.md @@ -1,41 +1,41 @@ # 围账 -回到 Fordedwinds 后,Guspu Frillyknots 没有再去见 Ral Fastenhatchets,也没有去找 Momuz。他做的第一件事,是约了 Perom Crazeowned 喝酒。Perom 是个做皮革生意的男人,不算有势力,但认识所有该认识的人。Guspu 问他:“被定罪的人,还能不能让人替他记账?”Perom 没答,只敬了他一杯酒。 +回到涉风渡后,古斯普·褶结没有再去见拉尔·缚斧,也没有去找莫穆兹。他做的第一件事,是约了佩罗姆·狂据喝酒。佩罗姆是个做皮革生意的男人,不算有势力,但认识所有该认识的人。古斯普问他:“被定罪的人,还能不能让人替他记账?”佩罗姆没答,只敬了他一杯酒。 -202 年,Perom 点了头。203 年,山民 Espu Bonestands 带着盐下山求见,Guspu 收下盐,让 Espu 守在北门外。矮人 Lolor Bronzescorched 也来了,她要矿区里的一个位置。Guspu 给了她名字,也给了活儿:盯住一切往东走的货。207 年,女 Goblin Dostngosp Jackalbrims 也把名字投到他门下。 +202 年,佩罗姆点了头。203 年,山民埃斯普·骨立带着盐下山求见,古斯普收下盐,让埃斯普守在北门外。矮人洛洛尔·铜焦也来了,她要矿区里的一个位置。古斯普给了她名字,也给了活儿:盯住一切往东走的货。207 年,女哥布林多斯特恩戈斯普·豺帽也把名字投到他门下。 -到那一年,他手里有人,也有位置。于是他决定对 Ral 动手。 +到那一年,他手里有人,也有位置。于是他决定对拉尔动手。 -那是一次构陷。他要在 The Volcano Of Ravens 的公堂上,给 Ral 安个贪税的罪名。他准备了伪造的账页,又借来几个信得过的喉咙。Ral 在城门口被拦下,背着一包账本上堂。有人递上那几页纸,说这是她的手迹。 +那是一次构陷。他要在渡鸦火山的公堂上,给拉尔安个贪税的罪名。他准备了伪造的账页,又借来几个信得过的喉咙。拉尔在城门口被拦下,背着一包账本上堂。有人递上那几页纸,说这是她的手迹。 -Ral 翻了一遍,抬头问:“谁写的?” +拉尔翻了一遍,抬头问:“谁写的?” 堂上没人应。 她说:“这墨不是我的。我记账不用这种纸。” -官差面面相觑。Guspu 在堂外没动。他算过她会争辩,没算过她随身带着十年的旧账,纸色、墨线、装订线一模一样。她翻开旧账,一页一页比对。堂上慢慢安静下来。 +官差面面相觑。古斯普在堂外没动。他算过她会争辩,没算过她随身带着十年的旧账,纸色、墨线、装订线一模一样。她翻开旧账,一页一页比对。堂上慢慢安静下来。 构陷失败了。 -Ral 走出公堂时没有看 Guspu。她只对身旁的人说:“回去把今天记下来。” +拉尔走出公堂时没有看古斯普。她只对身旁的人说:“回去把今天记下来。” -Guspu 学到一件事:一次栽赃压不垮她,那就把能买的人都买下来。210 年,他去找 Zutthan Yellplank,渡口的矮人,想买她一个晚上,让她放人过河堵住 Ral 的路。他开了高价。Zutthan 没应,第二天只在渡口多挂了两盏灯。那桩贿赂没成。 +古斯普学到一件事:一次栽赃压不垮她,那就把能买的人都买下来。210 年,他去找祖坦·啸板,渡口的矮人,想买她一个晚上,让她放人过河堵住拉尔的路。他开了高价。祖坦没应,第二天只在渡口多挂了两盏灯。那桩贿赂没成。 此后几年,他又试了四十七次。有的被拒,有的被拖,有的收了钱反悔。他夜里把一个个名字从簿子上画掉。那些人越是不肯,他越要留在手里。 -可他的圈子还是在涨。210 年,Onul Glowroofs 入局。215 年,Mudi Blazedbrushes 和 Stinthad Oilshove 入局。216 年,Ingish Steelgrouped 也来了。有人奔着他的手面,有人惧他,有人只是不想站在他的对面。他不再挑拣,只数人数。 +可他的圈子还是在涨。210 年,奥努尔·光顶入局。215 年,穆迪·焰刷和斯廷哈德·油推入局。216 年,英吉什·钢聚也来了。有人奔着他的手面,有人惧他,有人只是不想站在他的对面。他不再挑拣,只数人数。 -到 216 年冬,他已经不去想那场失败的构陷了。他甚至不再派人盯着 Ral 的屋子。他在城外高地上站了一会儿,问 Espu:“我现在有十几个人。她有几个?” +到 216 年冬,他已经不去想那场失败的构陷了。他甚至不再派人盯着拉尔的屋子。他在城外高地上站了一会儿,问埃斯普:“我现在有十几个人。她有几个?” -Espu 说:“一个记账的。” +埃斯普说:“一个记账的。” -Guspu 笑了一下:“不够。” +古斯普笑了一下:“不够。” -其实他真正想要的,不是除掉 Ral,而是让她听见那些名字,知道这个城终会把她围成一页摊不开的旧账。 +其实他真正想要的,不是除掉拉尔,而是让她听见那些名字,知道这个城终会把她围成一页摊不开的旧账。 -而那天夜里,Ral 的住处亮着两盏灯。她的账本上没写 Guspu 的名字,只添了一行: +而那天夜里,拉尔的住处亮着两盏灯。她的账本上没写古斯普的名字,只添了一行: -“216 年,Ingish Steelgrouped 入局。” +“216 年,英吉什·钢聚入局。” 字迹很稳,像是早就知道这页会在什么时候被翻开。 diff --git a/output/volumes/v1/chapters/003-219-228-p1.md b/output/volumes/v1/chapters/003-219-228-p1.md index 0dc7fe3..f710c68 100644 --- a/output/volumes/v1/chapters/003-219-228-p1.md +++ b/output/volumes/v1/chapters/003-219-228-p1.md @@ -1,19 +1,19 @@ # 锤子打不动的人 -219 年,Guspu 决定先切掉 Ral 最长的一根旧枝。他带了一本账去 Fordedwinds。Rigoth Stilledearthen 是 Ral 的旧识,替 Ral 看管铁锭。Guspu 把 Rigoth 在码头上的欠款一页页摊开:“我不是来讨债,我是让你选。你从 Ral 那里抽身,账我替你销。”Rigoth 问若不抽身会怎样。Guspu 收起账本:“会变成流言。”第二天,Rigoth 当众扔掉了与 Ral 的铁楔。第一个,削掉了。 +219 年,古斯普决定先切掉拉尔最长的一根旧枝。他带了一本账去涉风渡。里戈斯·静土是拉尔的旧识,替拉尔看管铁锭。古斯普把里戈斯在码头上的欠款一页页摊开:“我不是来讨债,我是让你选。你从拉尔那里抽身,账我替你销。”里戈斯问若不抽身会怎样。古斯普收起账本:“会变成流言。”第二天,里戈斯当众扔掉了与拉尔的铁楔。第一个,削掉了。 -221 年,Dostngosp Jackalbrims 正式与 Guspu 结契。Guspu 以为自己已经把 Ral 围紧。他让 Dostngosp 把一包铁屑和几张账页送进 The Volcano Of Ravens,说这些是 Ral 私吞 Fordedwinds 公共斤两的证据。他以为 Ral 的锤子再硬,也硬不过火山的舌头。可 The Volcano Of Ravens 把铁屑丢进炭火,烧出来却是一团软渣,不是 Ral 的钢。构陷失败。Guspu 在火山石阶上坐了一夜。他只知道:Ral 身边还有眼睛,而且比他多一副。 +221 年,多斯特恩戈斯普·豺帽正式与古斯普结契。古斯普以为自己已经把拉尔围紧。他让多斯特恩戈斯普把一包铁屑和几张账页送进渡鸦火山,说这些是拉尔私吞涉风渡公共斤两的证据。他以为拉尔的锤子再硬,也硬不过火山的舌头。可渡鸦火山把铁屑丢进炭火,烧出来却是一团软渣,不是拉尔的钢。构陷失败。古斯普在火山石阶上坐了一夜。他只知道:拉尔身边还有眼睛,而且比他多一副。 -222 年,Guspu 找到 Ducim Theatercrested,让他在戏台上唱 Ral 脚滑进铁水。Ducim 点头。从这年起,Fordedwinds 的酒馆里多了一出丑戏。唱的人笑,听的人笑,只有 Ral 没有笑。 +222 年,古斯普找到杜西姆·剧冠,让他在戏台上唱拉尔脚滑进铁水。杜西姆点头。从这年起,涉风渡的酒馆里多了一出丑戏。唱的人笑,听的人笑,只有拉尔没有笑。 -223 年,Onul Glowroofs 和 Ingish Steelgrouped 正式与 Guspu 结契。一个替他听,一个替他供铁。Guspu 在炉边对两人说:“说话的人、唱戏的人、听壁角的人,和运铁的船,都姓了鹰。”他第一次觉得,Ral 的墙正往下掉土。 +223 年,奥努尔·光顶和英吉什·钢聚正式与古斯普结契。一个替他听,一个替他供铁。古斯普在炉边对两人说:“说话的人、唱戏的人、听壁角的人,和运铁的船,都姓了鹰。”他第一次觉得,拉尔的墙正往下掉土。 -224 年,Ral 动了。他穿过东门去找 Zuntir Baldedattic,不要钱,只要他告诉自己 Guspu 的人每天过了几车、装了多少。Zuntir 收下话。这是 Ral 近几年第一次主动伸手。Guspu 听说了,在账房里砸了一块碳。他知道,Ral 不会只挨打。 +224 年,拉尔动了。他穿过东门去找尊提尔·秃阁,不要钱,只要他告诉自己古斯普的人每天过了几车、装了多少。尊提尔收下话。这是拉尔近几年第一次主动伸手。古斯普听说了,在账房里砸了一块碳。他知道,拉尔不会只挨打。 -225 年,Guspu 决定先打断 Ral 的一只手。他带人去了 Mortalpears,那里是 Ral 补给线的口子,把守者是 Goblin Uknol Thornticks,善在梨树林里埋尖桩。两人打了两次:第一次冒进,两个随从被穿了腿;第二次他亲自举盾压进林子。Uknol 退进雾里,没有死,但 Mortalpears 的路被踩平了。Guspu 回城,大衣上挂满梨刺。 +225 年,古斯普决定先打断拉尔的一只手。他带人去了殇梨,那里是拉尔补给线的口子,把守者是哥布林乌克诺尔·棘蜱,善在梨树林里埋尖桩。两人打了两次:第一次冒进,两个随从被穿了腿;第二次他亲自举盾压进林子。乌克诺尔退进雾里,没有死,但殇梨的路被踩平了。古斯普回城,大衣上挂满梨刺。 -226 年,轮到 Ral 下到 Fordedwinds 浅滩。Guspu 新派的收税人 Usel Fisherfair 带着六条船挨家翻货。Ral 没等船靠岸,提锤下水。两人在浅滩打了两次:头一次,Usel 的船被撞翻;第二次,Usel 放火烧了东边泊位。Ral 没吃大亏,但船坞焦了一半。这是他第一次砸人后,没听见自己笑。 +226 年,轮到拉尔下到涉风渡浅滩。古斯普新派的收税人乌塞尔·渔市带着六条船挨家翻货。拉尔没等船靠岸,提锤下水。两人在浅滩打了两次:头一次,乌塞尔的船被撞翻;第二次,乌塞尔放火烧了东边泊位。拉尔没吃大亏,但船坞焦了一半。这是他第一次砸人后,没听见自己笑。 -227 年,Guspu 在 Lashheroes 对上 Meng Walkclasped,此人是 Ral 从北方请来的打手,两把扣锤专砸铁链。打了两场:第一场,Guspu 后背裂了一道;第二场,他让 Ingish 夜里用钢水浇死了 Meng 的扣锤。Meng 骂着退走。Guspu 一句话没说,血在喉咙里来回滚。 +227 年,古斯普在鞭雄对上蒙·行扣,此人是拉尔从北方请来的打手,两把扣锤专砸铁链。打了两场:第一场,古斯普后背裂了一道;第二场,他让英吉什夜里用钢水浇死了蒙的扣锤。蒙骂着退走。古斯普一句话没说,血在喉咙里来回滚。 -228 年,Guspu 杀到 Liecats,撞上 Ngom Matchedmenaces。他上马时告诉自己:再削掉一个,Ral 就只剩空墙。可打到一半,他看见路边的草地全烧成了黑灰,忽然想不起这一路是谁先点的火。他攥紧缰绳,继续向前。Ral 的墙还在,但已经裂了。 +228 年,古斯普杀到卧猫,撞上恩戈姆·匹凶。他上马时告诉自己:再削掉一个,拉尔就只剩空墙。可打到一半,他看见路边的草地全烧成了黑灰,忽然想不起这一路是谁先点的火。他攥紧缰绳,继续向前。拉尔的墙还在,但已经裂了。 diff --git a/output/volumes/v1/figures.md b/output/volumes/v1/figures.md index 15a92a1..f87a0da 100644 --- a/output/volumes/v1/figures.md +++ b/output/volumes/v1/figures.md @@ -4,123 +4,123 @@ | 人物 | 种族 | 生卒 | 职业 | 事件数 | |---|---|---|---|---| -| Stobsa Boilpukes The Most | HYDRA | 生卒不详 | — | 191 | -| Raz Scorchedlanced The Hardy | COLOSSUS_BRONZE | 生卒不详 | — | 171 | -| Langgud Dawncats The Washed Seed | TITAN_3 | ?–204 | — | 168 | -| Zogast Tufttop The Decisive Key | HYDRA | 生卒不详 | — | 161 | +| Stobsa Boilpukes The Most | 九头蛇 | 生卒不详 | — | 191 | +| Raz Scorchedlanced The Hardy | 青铜巨像 | 生卒不详 | — | 171 | +| 朗古德 Dawncats The Washed Seed | TITAN_3 | ?–204 | — | 168 | +| Zogast Tufttop The Decisive Key | 九头蛇 | 生卒不详 | — | 161 | | Inefa Dawnorange The Snarling Puke | TITAN_7 | 生卒不详 | — | 145 | -| Gaspa Begunhog The Clean | HYDRA | 88–在世/不详 | — | 144 | -| Oka Tinglistened The Howl Of Prestige | CYCLOPS | 生卒不详 | — | 127 | -| Od Mucusrock The Gleams Of Grease | HYDRA | 生卒不详 | — | 122 | -| Ngumost Apesstrap The Mountainous | BIRD_ROC | 生卒不详 | — | 121 | -| Yare Sistersubmerge | ELF | 4–在世/不详 | — | 115 | +| Gaspa Begunhog The Clean | 九头蛇 | 88–在世/不详 | — | 144 | +| Oka Tinglistened The Howl Of Prestige | 独眼巨人 | 生卒不详 | — | 127 | +| Od Mucusrock The Gleams Of Grease | 九头蛇 | 生卒不详 | — | 122 | +| Ngumost Apesstrap The Mountainous | 大鹏 | 生卒不详 | — | 121 | +| Yare Sistersubmerge | 精灵 | 4–在世/不详 | — | 115 | | Otust Wondereddriven The Beloved | ETTIN | 生卒不详 | — | 113 | -| Ostzu Granitewanders The Flicker Of Intensity | CYCLOPS | 生卒不详 | — | 106 | +| Ostzu Granitewanders The Flicker Of Intensity | 独眼巨人 | 生卒不详 | — | 106 | | Are Flaxrose The Bearded | TITAN_2 | 生卒不详 | — | 103 | -| Quathari Holyglen | ELF | 0–在世/不详 | — | 98 | +| Quathari Holyglen | 精灵 | 0–在世/不详 | — | 98 | | Urer Sunsshore The Hairy | TITAN_9 | 生卒不详 | — | 97 | -| Irene Ramlarge The Strong | BIRD_ROC | 生卒不详 | — | 95 | -| Thaci Authoredferns | ELF | 77–在世/不详 | — | 87 | -| Lapama Bittentwig | ELF | 生卒不详 | — | 87 | -| Asada Darkbalances The Ordered Sewer | YETI | ?–224 | — | 86 | -| Kifino Latewings | ELF | 79–在世/不详 | — | 84 | +| Irene Ramlarge The Strong | 大鹏 | 生卒不详 | — | 95 | +| Thaci Authoredferns | 精灵 | 77–在世/不详 | — | 87 | +| Lapama Bittentwig | 精灵 | 生卒不详 | — | 87 | +| Asada Darkbalances The Ordered Sewer | 雪人 | ?–224 | — | 86 | +| Kifino Latewings | 精灵 | 79–在世/不详 | — | 84 | | Shigos Saffronjumps The Teal Berries | TITAN_6 | 生卒不详 | — | 83 | -| Avafi Rootskull | ELF | 10–在世/不详 | — | 83 | -| Ova Packvessels | ELF | 114–在世/不详 | — | 83 | -| Iru Sensedclam | ELF | 99–在世/不详 | — | 81 | -| Genam Searingdwell | HUMAN | 129–193 | — | 81 | -| Rine Clenchdrinkers The Legend Of Wilts | YETI | ?–232 | — | 80 | -| Thalu Shellbud | ELF | 43–在世/不详 | — | 80 | -| Nefola Wheeleagle | ELF | 生卒不详 | — | 78 | -| Domas Meetingtongs | DWARF | 103–在世/不详 | — | 78 | -| Langgud Tradebears The Eviscerated Chill Of Pregnancies | YETI | 生卒不详 | — | 77 | -| Erith Orbrelieve | DWARF | 71–222 | — | 77 | -| Evala Dalemoisten | ELF | 生卒不详 | — | 76 | -| Thone Mawpunch | ELF | 58–在世/不详 | — | 76 | -| Ilime Lobsterfancied | ELF | 110–在世/不详 | — | 76 | -| Kiros Cloudstones The Divine Delights | YETI | ?–219 | — | 74 | -| Quathari Skunkdive | ELF | 65–在世/不详 | — | 74 | -| Kivish Boltpartner | DWARF | 74–233 | — | 74 | -| Nemile Worldglisten | ELF | 79–在世/不详 | — | 74 | -| Lomifo Oakfill The Severe | YETI | ?–242 | — | 73 | -| Enkos Apepulp The Plain | HYDRA | ?–206 | — | 72 | -| Caraca Owlstrap | ELF | 73–在世/不详 | — | 72 | -| Lali Woodenpraise | ELF | 79–在世/不详 | — | 72 | -| Irene Biteglade | ELF | 生卒不详 | — | 72 | -| Ral Fastenhatchets | DWARF | 164–在世/不详 | — | 71 | -| Imimi Shorelines | ELF | 75–在世/不详 | — | 70 | -| Amala Leaptested | ELF | 72–在世/不详 | — | 69 | -| Salo Metblaze | ELF | 84–在世/不详 | — | 69 | -| Efami Churchcoasts | ELF | 121–在世/不详 | — | 69 | -| Themiyi Pinessplattered | ELF | 72–在世/不详 | — | 68 | -| Lolama Silkankle | ELF | 26–在世/不详 | — | 67 | +| Avafi Rootskull | 精灵 | 10–在世/不详 | — | 83 | +| Ova Packvessels | 精灵 | 114–在世/不详 | — | 83 | +| Iru Sensedclam | 精灵 | 99–在世/不详 | — | 81 | +| Genam Searingdwell | 人类 | 129–193 | — | 81 | +| Rine Clenchdrinkers The Legend Of Wilts | 雪人 | ?–232 | — | 80 | +| Thalu Shellbud | 精灵 | 43–在世/不详 | — | 80 | +| Nefola Wheeleagle | 精灵 | 生卒不详 | — | 78 | +| 多马斯 Meetingtongs | 矮人 | 103–在世/不详 | — | 78 | +| 朗古德·商熊「剖胎之寒」 | 雪人 | 生卒不详 | — | 77 | +| Erith Orbrelieve | 矮人 | 71–222 | — | 77 | +| 埃瓦拉 Dalemoisten | 精灵 | 生卒不详 | — | 76 | +| Thone Mawpunch | 精灵 | 58–在世/不详 | — | 76 | +| Ilime Lobsterfancied | 精灵 | 110–在世/不详 | — | 76 | +| Kiros Cloudstones The Divine Delights | 雪人 | ?–219 | — | 74 | +| Quathari Skunkdive | 精灵 | 65–在世/不详 | — | 74 | +| Kivish Boltpartner | 矮人 | 74–233 | — | 74 | +| Nemile Worldglisten | 精灵 | 79–在世/不详 | — | 74 | +| Lomifo Oakfill The Severe | 雪人 | ?–242 | — | 73 | +| Enkos Apepulp The Plain | 九头蛇 | ?–206 | — | 72 | +| Caraca Owlstrap | 精灵 | 73–在世/不详 | — | 72 | +| Lali Woodenpraise | 精灵 | 79–在世/不详 | — | 72 | +| Irene Biteglade | 精灵 | 生卒不详 | — | 72 | +| 拉尔·缚斧 | 矮人 | 164–在世/不详 | — | 71 | +| Imimi Shorelines | 精灵 | 75–在世/不详 | — | 70 | +| Amala Leaptested | 精灵 | 72–在世/不详 | — | 69 | +| Salo Metblaze | 精灵 | 84–在世/不详 | — | 69 | +| Efami Churchcoasts | 精灵 | 121–在世/不详 | — | 69 | +| Themiyi Pinessplattered | 精灵 | 72–在世/不详 | — | 68 | +| Lolama Silkankle | 精灵 | 26–在世/不详 | — | 67 | | Tobul Robustzenith The Mint Yell | GIANT | 生卒不详 | — | 66 | -| Yemi Goodclouds | ELF | 7–在世/不详 | — | 66 | +| Yemi Goodclouds | 精灵 | 7–在世/不详 | — | 66 | | Durad Meadowjumped The Paddle Of Fords | TITAN_1 | 生卒不详 | — | 65 | | Lek Willspecial The Meteor Of Fame | GIANT | 生卒不详 | — | 64 | | Darala Sportstrengths The Prestigious | GIANT | 生卒不详 | — | 64 | -| On Rocksfades The Mellow Mother | TROLL | ?–174 | — | 64 | -| Us Systemsanctum The Delightful Fragment Of Celebrations | YETI | 24–207 | — | 64 | -| Stinthad Glazedallies | DWARF | 74–225 | — | 64 | -| Thiliri Listenblaze | ELF | 85–在世/不详 | — | 64 | -| Cacame Birdcombats | ELF | 15–在世/不详 | — | 64 | -| Reg Runrings | DWARF | 50–220 | — | 63 | -| Imimi Skinmirrored | ELF | 95–在世/不详 | — | 63 | -| Cata Stylescarlet | ELF | 109–在世/不详 | — | 63 | -| Tirist Helmedtowns | DWARF | 110–在世/不详 | — | 63 | -| Eletha Orangeseason | ELF | 生卒不详 | — | 63 | -| Atera Earthenwiped | ELF | 152–在世/不详 | — | 63 | -| Zur Pucewanders The Blue Canyon | CYCLOPS | 生卒不详 | — | 62 | +| On Rocksfades The Mellow Mother | 巨魔 | ?–174 | — | 64 | +| Us Systemsanctum The Delightful Fragment Of Celebrations | 雪人 | 24–207 | — | 64 | +| 斯廷哈德 Glazedallies | 矮人 | 74–225 | — | 64 | +| Thiliri Listenblaze | 精灵 | 85–在世/不详 | — | 64 | +| Cacame Birdcombats | 精灵 | 15–在世/不详 | — | 64 | +| Reg Runrings | 矮人 | 50–220 | — | 63 | +| Imimi Skinmirrored | 精灵 | 95–在世/不详 | — | 63 | +| Cata Stylescarlet | 精灵 | 109–在世/不详 | — | 63 | +| 提里斯特 Helmedtowns | 矮人 | 110–在世/不详 | — | 63 | +| Eletha Orangeseason | 精灵 | 生卒不详 | — | 63 | +| Atera Earthenwiped | 精灵 | 152–在世/不详 | — | 63 | +| Zur Pucewanders The Blue Canyon | 独眼巨人 | 生卒不详 | — | 62 | | Itur Bristleknight The Sparkle Of Smiles | ETTIN | 生卒不详 | — | 62 | -| Sol Shellrisen The First | TROLL | ?–180 | — | 62 | -| Urdim Joinedlashed | DWARF | 98–在世/不详 | — | 62 | -| Lida Birdtraded | ELF | 124–在世/不详 | — | 62 | -| Cequova Lacycolored | ELF | 130–在世/不详 | — | 62 | -| Arane Coastalglens | ELF | 142–在世/不详 | — | 62 | -| Emene Torchtops The Adventurous | CYCLOPS | 生卒不详 | — | 61 | -| Alisa Embracedlovers | ELF | 28–在世/不详 | — | 61 | -| Mifava Fuchsiaown | ELF | 124–在世/不详 | — | 61 | -| Xuspgas Kissedhates | GOBLIN | 59–在世/不详 | — | 60 | -| Asob Machinestill | DWARF | 78–238 | — | 60 | -| Amayi Clearmusics | ELF | 80–在世/不详 | — | 60 | -| Themiyi Dreamsadored | ELF | 85–在世/不详 | — | 60 | -| Famime Sweetelders | ELF | 124–在世/不详 | — | 60 | -| Nemile Crazyglitter | ELF | 生卒不详 | — | 60 | -| Ana Waxedjade | ELF | 41–在世/不详 | — | 59 | -| Nemo Leopardanguished | ELF | 生卒不详 | — | 59 | -| Vema Wasprooters | ELF | 5–在世/不详 | — | 58 | -| Ova Guardedsuitor | ELF | 63–在世/不详 | — | 58 | -| Ngokang Singedoomed | GOBLIN | 74–在世/不详 | — | 58 | -| Kubuk Mountainpaddle | DWARF | 92–在世/不详 | — | 58 | -| Fikod Humidpaddled | DWARF | 92–在世/不详 | — | 58 | -| Zutthan Anguishink | DWARF | 98–在世/不详 | — | 58 | -| Rofa Sensecherished | ELF | 105–在世/不详 | — | 58 | -| Mimale Incenseflower | ELF | 107–在世/不详 | — | 58 | -| Caraca Hairdeer | ELF | 116–在世/不详 | — | 58 | -| Covema Questedwings | ELF | 生卒不详 | — | 58 | -| Rifa Bandedsatins | ELF | 121–在世/不详 | — | 58 | -| Tira Divedmerges | ELF | 153–在世/不详 | — | 58 | -| Ngebzo Pagesteals | GOBLIN | 64–在世/不详 | — | 57 | -| Apasi Howlriddled | ELF | 75–在世/不详 | — | 57 | -| Mimale Seaclinch | ELF | 111–在世/不详 | — | 57 | -| Ile Smiledpetal | ELF | 120–在世/不详 | — | 57 | -| Ave Naturaldances | ELF | 122–在世/不详 | — | 57 | -| Thiliri Hoofwinds | ELF | 生卒不详 | — | 57 | -| Snang Yawninghates | GOBLIN | 141–193 | — | 57 | +| Sol Shellrisen The First | 巨魔 | ?–180 | — | 62 | +| Urdim Joinedlashed | 矮人 | 98–在世/不详 | — | 62 | +| Lida Birdtraded | 精灵 | 124–在世/不详 | — | 62 | +| Cequova Lacycolored | 精灵 | 130–在世/不详 | — | 62 | +| Arane Coastalglens | 精灵 | 142–在世/不详 | — | 62 | +| Emene Torchtops The Adventurous | 独眼巨人 | 生卒不详 | — | 61 | +| Alisa Embracedlovers | 精灵 | 28–在世/不详 | — | 61 | +| Mifava Fuchsiaown | 精灵 | 124–在世/不详 | — | 61 | +| Xuspgas Kissedhates | 哥布林 | 59–在世/不详 | — | 60 | +| Asob Machinestill | 矮人 | 78–238 | — | 60 | +| Amayi Clearmusics | 精灵 | 80–在世/不详 | — | 60 | +| Themiyi Dreamsadored | 精灵 | 85–在世/不详 | — | 60 | +| Famime Sweetelders | 精灵 | 124–在世/不详 | — | 60 | +| Nemile Crazyglitter | 精灵 | 生卒不详 | — | 60 | +| 安娜 Waxedjade | 精灵 | 41–在世/不详 | — | 59 | +| Nemo Leopardanguished | 精灵 | 生卒不详 | — | 59 | +| Vema Wasprooters | 精灵 | 5–在世/不详 | — | 58 | +| Ova Guardedsuitor | 精灵 | 63–在世/不详 | — | 58 | +| 恩戈康 Singedoomed | 哥布林 | 74–在世/不详 | — | 58 | +| Kubuk Mountainpaddle | 矮人 | 92–在世/不详 | — | 58 | +| Fikod Humidpaddled | 矮人 | 92–在世/不详 | — | 58 | +| 祖坦 Anguishink | 矮人 | 98–在世/不详 | — | 58 | +| Rofa Sensecherished | 精灵 | 105–在世/不详 | — | 58 | +| Mimale Incenseflower | 精灵 | 107–在世/不详 | — | 58 | +| Caraca Hairdeer | 精灵 | 116–在世/不详 | — | 58 | +| Covema Questedwings | 精灵 | 生卒不详 | — | 58 | +| Rifa Bandedsatins | 精灵 | 121–在世/不详 | — | 58 | +| Tira Divedmerges | 精灵 | 153–在世/不详 | — | 58 | +| Ngebzo Pagesteals | 哥布林 | 64–在世/不详 | — | 57 | +| Apasi Howlriddled | 精灵 | 75–在世/不详 | — | 57 | +| Mimale Seaclinch | 精灵 | 111–在世/不详 | — | 57 | +| Ile Smiledpetal | 精灵 | 120–在世/不详 | — | 57 | +| Ave Naturaldances | 精灵 | 122–在世/不详 | — | 57 | +| Thiliri Hoofwinds | 精灵 | 生卒不详 | — | 57 | +| Snang Yawninghates | 哥布林 | 141–193 | — | 57 | | Olzul Masterbrains The Remarkable | FORGOTTEN_BEAST_76 | 生卒不详 | — | 56 | -| Asne Ecrutaken The Emerald Perfection | CYCLOPS | 生卒不详 | — | 56 | -| Amxu Hateflashes | GOBLIN | 75–在世/不详 | — | 56 | -| Lapama Plungemoths | ELF | 118–在世/不详 | — | 56 | -| Rathe Grottovises | ELF | 45–在世/不详 | — | 56 | -| Ula Thunderedmurk | ELF | 133–在世/不详 | — | 56 | -| Kogan Herooar | DWARF | 140–在世/不详 | — | 56 | -| Guspu Frillyknots | EAGLE_MAN | 151–246 | — | 56 | -| Dadu Twinklingflashed The Contested | CYCLOPS | 生卒不详 | — | 55 | -| Geshud Roughentered | DWARF | 35–197 | — | 55 | -| Arile Pristinefuture | ELF | 63–在世/不详 | — | 55 | -| Ilathe Frenzydeer | ELF | 70–在世/不详 | — | 55 | -| Nine Sweetnessholds | ELF | 70–在世/不详 | — | 55 | -| Urvad Basissalve | DWARF | 110–在世/不详 | — | 55 | -| Yare Snarledbirth | ELF | 95–在世/不详 | — | 55 | -| Itha Sportsongs | ELF | 生卒不详 | — | 55 | -| Ducim Pickices | DWARF | 136–在世/不详 | — | 55 | +| Asne Ecrutaken The Emerald Perfection | 独眼巨人 | 生卒不详 | — | 56 | +| 阿姆苏 Hateflashes | 哥布林 | 75–在世/不详 | — | 56 | +| Lapama Plungemoths | 精灵 | 118–在世/不详 | — | 56 | +| Rathe Grottovises | 精灵 | 45–在世/不详 | — | 56 | +| Ula Thunderedmurk | 精灵 | 133–在世/不详 | — | 56 | +| Kogan Herooar | 矮人 | 140–在世/不详 | — | 56 | +| 古斯普·褶结 | 鹰人 | 151–246 | — | 56 | +| Dadu Twinklingflashed The Contested | 独眼巨人 | 生卒不详 | — | 55 | +| Geshud Roughentered | 矮人 | 35–197 | — | 55 | +| Arile Pristinefuture | 精灵 | 63–在世/不详 | — | 55 | +| Ilathe Frenzydeer | 精灵 | 70–在世/不详 | — | 55 | +| Nine Sweetnessholds | 精灵 | 70–在世/不详 | — | 55 | +| Urvad Basissalve | 矮人 | 110–在世/不详 | — | 55 | +| Yare Snarledbirth | 精灵 | 95–在世/不详 | — | 55 | +| Itha Sportsongs | 精灵 | 生卒不详 | — | 55 | +| 杜西姆 Pickices | 矮人 | 136–在世/不详 | — | 55 | diff --git a/output/volumes/v1/timeline.md b/output/volumes/v1/timeline.md index 0565416..53a069b 100644 --- a/output/volumes/v1/timeline.md +++ b/output/volumes/v1/timeline.md @@ -13,7 +13,7 @@ - **2** [生死] hf died · hfid=Vema Seedanguished · site_id=Nutssound - **2** [生死] hf died · hfid=Masami Nightbeak · site_id=Nutssound - **2** [生死] hf died · hfid=Athe Saffronboot · site_id=Nutssound -- **2** [生死] hf died · hfid=Amxu Flydreamy · site_id=Scalysatins +- **2** [生死] hf died · hfid=阿姆苏 Flydreamy · site_id=Scalysatins - **2** [生死] hf died · hfid=Sazir Polishedlances · site_id=Amazedmirrored - **2** [生死] hf died · hfid=Bembul Silverygroove · site_id=Amazedmirrored - **2** [生死] hf died · hfid=Urvad Rayspaints · site_id=Amazedmirrored @@ -21,14 +21,14 @@ - **2** [生死] hf died · hfid=Rovod Abbeybolt · site_id=Amazedmirrored - **2** [生死] hf died · hfid=Zuglar Crowdedmine · site_id=Amazedmirrored - **2** [生死] hf died · hfid=Urvad Bowelguild · site_id=Amazedmirrored -- **2** [生死] hf died · hfid=Domas Brownlashed · site_id=Amazedmirrored +- **2** [生死] hf died · hfid=多马斯 Brownlashed · site_id=Amazedmirrored - …另有 324 条次要事件未列 ## 10s - **10** [生死] hf died · hfid=Uthra Hardyrake · site_id=Pathlance - **11** [生死] hf died · hfid=Zolak Werecoil · site_id=Stretchedvice -- **11** [生死] hf died · hfid=Utes Lieshut · site_id=Stretchedvice +- **11** [生死] hf died · hfid=乌特斯 Lieshut · site_id=Stretchedvice - **11** [生死] hf died · hfid=Hiner Plaitedangels · site_id=Praisepot - **12** [生死] hf died · hfid=Ubbul Crewsold - **12** [生死] hf died · hfid=Coce Willglimmered @@ -64,7 +64,7 @@ - **30** [生死] hf died · hfid=Nganiz Flagroars - **30** [生死] hf died · hfid=Mubun Slowsprayed -- **30** [生死] hf died · hfid=Mosus Parchedsyrup · site_id=Wallwhipped +- **30** [生死] hf died · hfid=莫苏斯 Parchedsyrup · site_id=Wallwhipped - **30** [生死] hf died · hfid=Olon Cobaltkin · site_id=Wallwhipped - **30** [生死] hf died · hfid=Sigun Elderposts · site_id=Wallwhipped - **30** [生死] hf died · hfid=Lor Crestedrock · site_id=Wallwhipped @@ -125,7 +125,7 @@ - **62** [生死] hf died · hfid=Dasar Rackpacked - **62** [生死] hf died · hfid=Ayara Rumoredjumps - **62** [生死] hf died · hfid=Lor Rawworks -- **62** [生死] hf died · hfid=Onul Entrancestandards +- **62** [生死] hf died · hfid=奥努尔 Entrancestandards - **63** [生死] hf died · hfid=Ongslun Headrespect - **63** [生死] hf died · hfid=Limili Conjurerulers - **64** [生死] hf died · hfid=Jepum Murderedsiege @@ -140,13 +140,13 @@ - **70** [生死] hf died · hfid=Pesor Castlecharred - **70** [生死] hf died · hfid=Stozu Witchyawned · site_id=Hauntblack - **70** [生死] hf died · hfid=Azstrog Scorpiongilt · site_id=Releaselabored -- **70** [生死] hf died · hfid=Ngokang Terrorbears · site_id=Releaselabored +- **70** [生死] hf died · hfid=恩戈康 Terrorbears · site_id=Releaselabored - **70** [生死] hf died · hfid=Melbil Cloistercovers · site_id=Releaselabored - **70** [生死] hf died · hfid=Ngoso Lostscorpions · site_id=Releaselabored -- **70** [生死] hf died · hfid=Ngokang Phantommonsters · site_id=Releaselabored -- **70** [生死] hf died · hfid=Asmel Ringmeshes · site_id=Releaselabored +- **70** [生死] hf died · hfid=恩戈康 Phantommonsters · site_id=Releaselabored +- **70** [生死] hf died · hfid=阿斯梅尔 Ringmeshes · site_id=Releaselabored - **70** [生死] hf died · hfid=Ago Entrymonster · site_id=Releaselabored -- **70** [生死] hf died · hfid=Mosus Glovedbraved · site_id=Releaselabored +- **70** [生死] hf died · hfid=莫苏斯 Glovedbraved · site_id=Releaselabored - **70** [生死] hf died · hfid=Snodub Savantsteals · site_id=Releaselabored - …另有 1209 条次要事件未列 @@ -174,7 +174,7 @@ - **90** [生死] hf died · hfid=Angos Witheredentrance - **90** [生死] hf died · hfid=Rodem Matchgrieved - **90** [生死] hf died · hfid=Doce Finddives -- **90** [生死] hf died · hfid=Ongu Sensecage · site_id=Galeclods +- **90** [生死] hf died · hfid=翁古 Sensecage · site_id=Galeclods - **90** [生死] hf died · hfid=Erush Boardedsabres · site_id=Galeclods - **90** [生死] hf died · hfid=Mones Royalnestles · site_id=Galeclods - **90** [生死] hf died · hfid=Bathru Cookplots · site_id=Galeclods @@ -232,7 +232,7 @@ - **120** [生死] hf died · hfid=Agen Jeststrangers - **120** [生死] hf died · hfid=Rabin Gleeden - **120** [生死] hf died · hfid=Frudulutrolbus -- **120** [生死] hf died · hfid=Perom Polishbreeches · site_id=Strapsong +- **120** [生死] hf died · hfid=佩罗姆 Polishbreeches · site_id=Strapsong - **120** [生死] hf died · hfid=Kadol Mirrorpost · site_id=Spinestheater - **120** [生死] hf died · hfid=Kubuk Covenroom · site_id=Spinestheater - **120** [生死] hf died · hfid=Edzul Palacedwelled · site_id=Spinestheater @@ -270,7 +270,7 @@ - **140** [生死] hf died · hfid=Bale Lureplated - **140** [生死] hf died · hfid=Nifih Wingkissed - **140** [生死] hf died · hfid=Anir Dreamdimples -- **140** [生死] hf died · hfid=Ngom Staffspider · site_id=Nestleaders +- **140** [生死] hf died · hfid=恩戈姆 Staffspider · site_id=Nestleaders - **140** [生死] hf died · hfid=Tise Furylake · site_id=Nestleaders - **141** [生死] hf died · hfid=Manorpears - **141** [生死] hf died · hfid=Sosma Puzzlecurious @@ -325,7 +325,7 @@ - **170** [生死] hf died · hfid=Diso Orangesteam - **170** [生死] hf died · hfid=Dosheb Riverbalances - **170** [生死] hf died · hfid=Ejel Crestknowledge -- **170** [生死] hf died · hfid=Someg Lightnourished +- **170** [生死] hf died · hfid=索梅格 Lightnourished - **170** [生死] hf died · hfid=Ismir Fruityprice - **170** [生死] hf died · hfid=Rabin Counselledsalve - …另有 2129 条次要事件未列 @@ -449,7 +449,7 @@ - **240** [生死] hf died · hfid=Hushflesh - **240** [生死] hf died · hfid=Omud Taxpokers - **240** [生死] hf died · hfid=Wimad Riddledcities -- **240** [生死] hf died · hfid=Flowerown The Climactic Song Of Summer +- **240** [生死] hf died · hfid=Flowerown The Climactic 松 Of Summer - **240** [生死] hf died · hfid=Quemer Blanketbasin - **240** [生死] hf died · hfid=Rozmo Conjuredclenched - **240** [生死] hf died · hfid=Ugrad Lashedhail diff --git a/tests/test_localize.py b/tests/test_localize.py new file mode 100644 index 0000000..fd201b2 --- /dev/null +++ b/tests/test_localize.py @@ -0,0 +1,119 @@ +"""专名本土化的回归测试。 + +重点盯住两个曾经真实踩过的坑: +1. 只处理全名,漏掉正文里大量使用的简称(`Ral`)与单呼的姓(`Fastenhatchets`)。 +2. `YETI` 这类全大写枚举只改首字母得到 `YETI`,永远匹配不上正文里的 `Yeti`。 +""" +from __future__ import annotations + +import sys +from pathlib import Path + +sys.path.insert(0, str(Path(__file__).resolve().parents[1])) + +from dfannals import glossary, localize + + +def test_title_form_lowercases_tail() -> None: + assert localize.title_form("YETI") == "Yeti" + assert localize.title_form("EAGLE_MAN") == "Eagle_man" + assert localize.title_form("fastenhatchets") == "Fastenhatchets" + + +def test_person_full_name() -> None: + assert localize.translate_person("Ral Fastenhatchets") == "拉尔·缚斧" + assert localize.translate_person("Guspu Frillyknots") == "古斯普·褶结" + assert localize.translate_person("Rigoth Stilledearthen") == "里戈斯·静土" + + +def test_person_with_epithet() -> None: + name = "Langgud Tradebears The Eviscerated Chill Of Pregnancies" + assert localize.translate_person(name) == "朗古德·商熊「剖胎之寒」" + + +def test_person_unknown_returns_none() -> None: + assert localize.translate_person("Zzzq Unknownsurname") is None + + +def test_place_and_epithet() -> None: + assert localize.translate_place("Fordedwinds") == "涉风渡" + assert localize.translate_place("Paperhushed") == "纸寂" + assert localize.translate_place("Gloryholes The Trickery Of Mornings") == "荣耀穴(晨之诡计)" + + +def test_group_translation() -> None: + assert localize.translate_group("The Volcano Of Ravens") == "渡鸦火山" + + +def test_race_enum_and_display_form() -> None: + assert localize.translate_race("YETI") == "雪人" + assert localize.translate_race("DWARF") == "矮人" + assert localize.translate_race("UNKNOWN_RACE") == "UNKNOWN_RACE" + + +def _fake_translator() -> localize.Translator: + """不依赖真实世界数据的小翻译器,专测替换顺序。""" + translator = localize.Translator( + people={"Ral Fastenhatchets": "拉尔·缚斧", "Rigoth Stilledearthen": "里戈斯·静土"}, + places={"Fordedwinds": "涉风渡"}, + groups={"The Volcano Of Ravens": "渡鸦火山"}, + stems={"Ral": "拉尔", "Rigoth": "里戈斯"}, + surnames={"Fastenhatchets": "缚斧"}, + races={"Yeti": "雪人", "EAGLE_MAN": "鹰人"}, + ) + return translator + + +def test_render_full_name_wins_over_short_name() -> None: + out = _fake_translator().render("Ral Fastenhatchets守着Fordedwinds。") + assert out == "拉尔·缚斧守着涉风渡。", out + + +def test_render_short_name_and_bare_surname() -> None: + out = _fake_translator().render("Ral对Rigoth说:她那一支姓Fastenhatchets。") + assert "拉尔" in out and "里戈斯" in out and "缚斧" in out, out + assert not any(ch.isascii() and ch.isalpha() for ch in out), out + + +def test_render_race_display_form() -> None: + out = _fake_translator().render("一个Yeti站了起来。军团是EAGLE_MAN。") + assert "雪人" in out and "鹰人" in out, out + + +def test_render_tidies_spaces() -> None: + out = _fake_translator().render("Ral 说 完 就 走 了") + assert "拉尔" in out and "拉尔 说" not in out, out + + +def test_accepted_includes_pieces() -> None: + accepted = _fake_translator().accepted() + assert "拉尔·缚斧" in accepted + assert "拉尔" in accepted and "缚斧" in accepted, sorted(accepted) + + +def test_glossary_tables_are_lowercase_keys() -> None: + for table in (glossary.STEMS, glossary.SURNAMES, glossary.PLACES): + for key in table: + assert key == key.lower(), f"{key} 应小写,否则 title_form 对不上" + + +def _main() -> int: + tests = [v for k, v in sorted(globals().items()) if k.startswith("test_") and callable(v)] + failed = 0 + for fn in tests: + try: + fn() + except AssertionError as exc: + failed += 1 + print(f" ✗ {fn.__name__}: {exc}") + except Exception as exc: # noqa: BLE001 + failed += 1 + print(f" ✗ {fn.__name__}: {type(exc).__name__}: {exc}") + else: + print(f" ✓ {fn.__name__}") + print(f"\n{len(tests) - failed}/{len(tests)} 通过") + return 1 if failed else 0 + + +if __name__ == "__main__": + sys.exit(_main())