# Rust 构造器
## 你会学到什么
- 直接用 Rust 构造 `PulseSequence`、`PulsePhrase` 和 `PulseSong`。
- 使用 `PulseSampleClip` 和 `PulseMidiClip` 参与编曲。
- 理解什么时候 Rust 构造比 Lua 脚本更适合。
- 保持 Rust 构造路径和 Lua DSL 的语义一致。
## 适合谁读
如果你的音乐由程序生成、需要强类型检查,或者宿主不希望暴露 Lua 脚本,读本章。
## 前置知识
- [嵌入 Lua](embedding-lua.md)
- [心智模型](../00-overview/mental-model.md)
## 心智模型
Lua DSL 背后就是 Rust 构造器。`pulse.sequence():notes(...):durations(...)` 对应 `PulseSequence::new().with_notes(...).with_durations(...)`。直接用 Rust 不会绕过验证,它仍然返回 `PulseResult` 并检查范围。
Rust 构造适合机器生成和宿主集成;Lua 脚本适合创作者直接编辑。
## 最小可运行例子
```rust
use mlua_pulse::composition::{PulsePhrase, PulseSequence, PulseSong};
use mlua_pulse::effects::{effect_from_options, EffectOptions};
use mlua_pulse::export::ExportOptions;
use mlua_pulse::{files, theory};
fn main() -> mlua_pulse::PulseResult<()> {
let sequence = PulseSequence::new()
.with_notes(theory::scale("C4", "ionian")?)
.with_durations(vec![0.25, 0.25, 0.25, 0.25, 0.5, 0.5, 0.5, 1.0])
.with_instrument("electric_piano")
.with_volume(0.5)?
.with_velocity(0.62)?;
let phrase = PulsePhrase::new()
.add_sequence(sequence)
.with_repeat_times(2)?;
let song = PulseSong::new()
.with_tempo(112.0)?
.add_phrase(phrase)
.with_master_effect(effect_from_options("limiter", EffectOptions::Preset("standard".into()))?);
let options = ExportOptions::new().with_rms_normalization(-16.0, -1.0)?;
files::export_with_options(&song, "output/rust-builder.wav", options)
}
```
## 参数和边界
`PulseSequence` 保存单音或和弦事件、时值、乐器、合成器、效果、起始偏移、音量、声像和力度。音符/和弦数量必须匹配 durations。
`PulsePhrase` 可以包含 sequence、drum grid、sample clip 和 midi clip,并设置重复次数。`PulseSong` 是最终容器,可以添加素材、段落和 master effects。
`PulseSampleClip::new(path)` 支持 slice、reverse、loop、normalize、fade、pitch shift、time stretch、rate、gain、track、volume、pan、effect。`PulseMidiClip` 可以由 `files::import_midi(path)?.as_clip()` 得到,再设置 `with_start_at`、`with_track`、`with_volume`、`with_pan`、`with_repeat_times` 和效果。
## 常见陷阱
Rust 构造器方法有些会返回 `PulseResult<Self>`,不要随手 `unwrap()`。错误信息对用户很有价值。
不要在 Rust 侧构造无边界音量、负时值或无效采样参数再期待 Lua 层拦截。直接构造时,Rust 验证就是边界。
MIDI 导出不会嵌入采样音频,也不会保存音频效果。Rust 路径和 Lua 路径的格式限制一致。
## 进阶用法
混合使用很自然:Rust 生成基础结构,Lua 写最终编排;或 Lua 写作品,Rust 负责批量导出和路径管理。关键是只让一层拥有最终时间线,避免 Rust 和 Lua 各自重复展开段落。
对于生成式音乐,Rust 可以先生成数据,再传给 Lua;也可以直接调用 `generators` 模块构造 `PulseSequence`。如果目标用户会调音乐,保留 Lua 层通常更友好。
## 相关章节
- [Rust API](../06-reference/rust-api.md)
- [采样与 MIDI](../01-lua-composition/samples-midi.md)
- [错误处理](error-handling.md)
- [WAV、FLAC、MIDI](../04-export/wav-flac-midi.md)