跳转至

M8 · instruction 通道:文本注入 vs 声学注入

状态 ✅ 成立
日期 提出 2026-08-15,跑完 2026-08-17
一句话 instruct 能给情感类别但给不了强度(程度副词的单调率 22.9%,随机基线 16.7%),且它改的是能量而几乎不动 F0
上游 ← 用户想法「把当前的 ref 模式换成 instruction 模式」
下游 \(\alpha\) 的连续强度有了明确的差异化位置,且不依赖调色板是否成功

1 动机

CosyVoice 自带 instruct 模式(自然语言指令控制)。用户要求把 ref 模式换成它,听听结果。 这同时能回答一个对定位很关键的问题:instruct 已经能做的事,我们的 \(\alpha\) 还有什么必要?

2 代码事实(已核实,非推测)

def frontend_instruct2(tts_text, instruct_text, prompt_wav, ...):
    model_input = self.frontend_zero_shot(tts_text, instruct_text, prompt_wav, ...)
    del model_input['llm_prompt_speech_token']      # ← 关键
    return model_input

instruct 模式就是 zero-shot 模式,只是把参考的文本槽换成指令文本、 并删掉 LLM 的声学 prompt token。flow 侧仍拿到参考 mel(音色)。

所以两条注入通道正交:

情感从哪注入
instruct 文本通道(指令文字)
我们(ref 模式) 声学 token 通道(正是 instruct 删掉的那条)

格式坑

CosyVoice3 的 LLM 断言文本含 <|endofprompt|>(llm.py:479), 指令必须写在它之前:"You are a helpful assistant. 请用悲伤的语气说这句话。<|endofprompt|>"。 格式取自仓库自带 example.py,不是臆造。初次按直觉写(指令在后)直接 assert 失败。

3 设计

自变量 情感如何指定(ref 声学通道 / 三档强度指令)
控制量 同目标文本、同音色参考(中性录音)、同种子、同 ckpt
对照 neutral(α≡0)为基线;ref_alpha1 为我们的方法
判据 「稍微 → 无副词 → 非常」的声学变化量是否单调递增不经过 emotion2vec
n 12 句 × 4 情感 = 48 条语句 × 5 档 = 240 条

音色参考为何统一用中性录音

instruct 模式若用情感录音,情感会经 flow 前缀泄漏,就分不清是文本通道还是声学通道起的作用。 ref 模式则必须用情感录音 —— 那是它的定义。这一处不对齐是模式差异本身,不是引入的混杂。

4 运行

CUDA_VISIBLE_DEVICES=7 python emo/exp/M8_instruct/run.py \
    --ckpt _incoming/v4_epoch5.pt --manifest manifests/esd_parallel.jsonl \
    --out_dir outputs/m8_instruct --n_keys 12
python emo/exp/M8_instruct/analyze.py
240 条 / 卡 7 / 0 报错。

5 结果

定量(n=48 条语句,统计量 = 跨语句中位数)

|ΔF0| /Hz |Δ能量| /dB |Δ谱倾斜| /dB Δ时长 /s
稍微 21.9 6.53 0.94 −0.52
(无副词) 21.4 5.88 0.83 −0.40
非常 16.5 6.65 0.83 −0.38
ref 模式 α=1 79.0 6.32 2.18 +0.10

H1 检验:强度阶梯是否单调?

F0      21.88 → 21.40 → 16.48 Hz   ❌ 反而递减
能量     6.53 →  5.88 →  6.65 dB   ❌ 不单调
谱倾斜    0.94 →  0.83 →  0.83 dB   ❌ 不单调

逐语句单调比例(能量) 22.9%   n=48   随机基线 1/6 = 16.7%

instruct 的强度阶梯

四个情感里只有 Happy(蓝)单调递增;Sad(绿)明显反向 —— 「非常悲伤」的能量变化(3.1 dB)反而只有「稍微悲伤」(6.4 dB)的一半。 程度副词没有系统性效果。

定性 —— 直接听

同一句(0001_text00000)、同一情感(Sad)、同种子:

中性 ref 模式 α=1 instruct「稍微」 instruct(无副词) instruct「非常」

后三条听起来强度差不多 —— 这就是「程度副词没有系统性效果」的听感对应。 而 ref 模式那条的音高走向明显不同(ΔF0 79 Hz vs instruct 的 ~20 Hz)。

6 结论

H1 成立:instruct 给得了类别,给不了强度。 逐语句单调率 22.9% 对随机基线 16.7% —— 几乎等于瞎猜。

而且两条通道改的东西不一样(这是本实验计划外的收获):

ΔF0 Δ能量 Δ谱倾斜 Δ时长
ref(声学通道) 79.0 Hz 6.32 dB 2.18 dB +0.10 s
instruct(文本通道) ~20 Hz ~6.3 dB ~0.85 dB −0.4 s
  • F0 差 4 倍、谱倾斜差 2.6 倍,但能量几乎相同
  • 时长方向相反:ref 模式让悲伤变长(+0.10 s,符合真实录音的 Sad 1.12×), instruct 反而让它变短(−0.4 s)

→ 声学通道动的是音高与音色,文本通道主要动响度

边界:本实验只测声学量,不能断言 instruct 的情感"不像" —— 只能说它在这些物理维度上的变化模式与 ref 模式不同、且不随程度副词单调。 感知层面的比较仍需人工听测或解决 G1

7 坑

  1. 指令格式:<|endofprompt|> 必须在指令之后。按直觉写成前缀会 assert 失败。 → 教训:接口格式查仓库自带 example,别按直觉猜。
  2. n=1 的探针误导过我。单条试听时三档时长是 3.16 / 4.36 / 5.00 s,看着完美单调, 我当时记为「好兆头」。n=48 时该单调性消失(−0.52 / −0.40 / −0.38,幅度仅 0.14 s)。 → 印证方法论 §5.6:n<10 只作线索。
  3. instruct 删掉声学 prompt 后音色只靠 flow 参考 —— 本实验未量化 SECS 影响, 属已知缺口。

8 引出

\(\alpha\) 的连续强度控制有了明确的差异化位置:instruct 做不到这件事。 且这条结论不依赖调色板是否成功,属于即使混合线全线失败也仍然站得住的贡献。 → 未做:instruct 与 \(\alpha\) 组合(类别 + 强度)。见 OPEN G6