V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX  ›  lijiachang  ›  全部回复第 1 页 / 共 1 页
回复总数  6
17 小时 49 分钟前
回复了 Cola98 创建的主题 Rust 请教一个 Rust 问题,提前祝大家中秋节快乐
问题所在:
1. 在主循环中,每次遇到 FA 标志时都创建了新的 AuxInfo ,且覆盖了之前的值
2. AuxInfo::parse 方法每次只处理一个字段,而不是累积所有字段

解决方案,我们有两种处理方式:

方案 1 - 修改 ParserFactory::parse 方法,使用 Vec 收集所有 AUX 信息,最后合并:

```rust
impl ParserFactory {
pub fn parse(rdb_context: &[u8]) -> Result<RDBInfo> {
let mut cursor = Cursor::new(rdb_context);
let base_info = BaseInfo::parse(&mut cursor)?;
let rdb_version: usize = base_info.rdb_version.parse().expect("Not a valid number");
let mut aux_infos = Vec::new(); // 存储所有 AUX 信息
let mut db_info = None;

if rdb_version < 7 {
aux_infos = Vec::new();
};

loop {
let mut flag_byte = [0;1];
if cursor.read_exact(&mut flag_byte).is_err() {
break
}
match flag_byte[0] {
FA => {
if let Some(aux_info) = AuxInfo::parse(&mut cursor)? {
aux_infos.push(aux_info);
}
}
FE => {
db_info = Some(DbInfo::parse(&mut cursor)?);
}
FF => {
println!("parse done.");
break
}
_ => {
continue;
}
}
}

// 合并所有 AUX 信息
let final_aux_info = aux_infos.into_iter().fold(
AuxInfo {
redis_server_version: String::new(),
used_mem: 0,
},
|mut acc, curr| {
if !curr.redis_server_version.is_empty() {
acc.redis_server_version = curr.redis_server_version;
}
if curr.used_mem != 0 {
acc.used_mem = curr.used_mem;
}
acc
}
);

let rdb_info = RDBInfo {
base_info,
aux_info: final_aux_info,
};

Ok(rdb_info)
}
}
```

方案 2 - 修改 AuxInfo::parse 方法,让它保持当前状态:

```rust
impl Parser for AuxInfo {
fn parse(cursor: &mut Cursor<&[u8]>) -> Result<Option<AuxInfo>> {
let aux_name = parser_aux_name(cursor)?;

// 根据字段名返回对应的 AuxInfo
let aux_info = match aux_name.as_str() {
"redis-ver" => {
Some(AuxInfo {
redis_server_version: parser_aux_value(cursor)?,
used_mem: 0,
})
}
"used-mem" => {
Some(AuxInfo {
redis_server_version: String::new(),
used_mem: parser_aux_value(cursor)?.parse::<usize>()
.expect("Failed to parse used-mem"),
})
}
_ => None
};

Ok(aux_info)
}
}
```

我建议使用方案 1 ,因为:
1. 更清晰地表达了数据收集的过程
2. 更容易扩展,如果将来需要添加新的 AUX 字段
3. 数据处理逻辑更集中,便于维护

关键改进点:
1. 使用 Vec 收集所有 AUX 信息
2. 使用 fold 方法合并所有 AUX 信息
3. 保留了非空/非零值,避免数据丢失

你需要注意的地方:
1. 确保 parser_aux_name 和 parser_aux_value 正确处理了数据
2. 考虑错误处理机制,可能需要添加更多的错误类型
3. 可以添加日志来跟踪解析过程
IDE 看了就摇头
257 天前
回复了 craftx 创建的主题 Python 求基于 Python 开发大流量在线服务的经验教训
如果团队技术栈是 Python 的话,用 Django 没什么问题
2023-04-15 13:57:31 +08:00
回复了 bytesfold 创建的主题 Python PyCharm 2023.1 released
旧 UI 还能用吧
关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   2784 人在线   最高记录 6679   ·     Select Language
创意工作者们的社区
World is powered by solitude
VERSION: 3.9.8.5 · 19ms · UTC 09:32 · PVG 17:32 · LAX 01:32 · JFK 04:32
Developed with CodeLauncher
♥ Do have faith in what you're doing.