如何从 Rust 中的文件读取结构? [英] How to read a struct from a file in Rust?

查看:15
本文介绍了如何从 Rust 中的文件读取结构?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有没有办法直接从 Rust 的文件中读取结构?我的代码是:

Is there a way I can read a structure directly from a file in Rust? My code is:

use std::fs::File;

struct Configuration {
    item1: u8,
    item2: u16,
    item3: i32,
    item4: [char; 8],
}

fn main() {
    let file = File::open("config_file").unwrap();

    let mut config: Configuration;
    // How to read struct from file?
}

如何将我的配置直接从文件读入 config?这甚至可能吗?

How would I read my configuration directly into config from the file? Is this even possible?

推荐答案

给你:

use std::io::Read;
use std::mem;
use std::slice;

#[repr(C, packed)]
#[derive(Debug, Copy, Clone)]
struct Configuration {
    item1: u8,
    item2: u16,
    item3: i32,
    item4: [char; 8],
}

const CONFIG_DATA: &[u8] = &[
    0xfd, // u8
    0xb4, 0x50, // u16
    0x45, 0xcd, 0x3c, 0x15, // i32
    0x71, 0x3c, 0x87, 0xff, // char
    0xe8, 0x5d, 0x20, 0xe7, // char
    0x5f, 0x38, 0x05, 0x4a, // char
    0xc4, 0x58, 0x8f, 0xdc, // char
    0x67, 0x1d, 0xb4, 0x64, // char
    0xf2, 0xc5, 0x2c, 0x15, // char
    0xd8, 0x9a, 0xae, 0x23, // char
    0x7d, 0xce, 0x4b, 0xeb, // char
];

fn main() {
    let mut buffer = CONFIG_DATA;

    let mut config: Configuration = unsafe { mem::zeroed() };

    let config_size = mem::size_of::<Configuration>();
    unsafe {
        let config_slice = slice::from_raw_parts_mut(&mut config as *mut _ as *mut u8, config_size);
        // `read_exact()` comes from `Read` impl for `&[u8]`
        buffer.read_exact(config_slice).unwrap();
    }

    println!("Read structure: {:#?}", config);
}

在这里试试(针对 Rust 1.38 更新)

Try it here (Updated for Rust 1.38)

然而,您需要小心,因为不安全的代码是不安全的.在 slice::from_raw_parts_mut() 调用之后,同一数据同时存在两个可变句柄,这违反了 Rust 别名规则.因此,您希望在尽可能短的时间内保留从结构中创建的可变切片.我还假设您知道字节顺序问题 - 上面的代码绝不是可移植的,如果在不同类型的机器(例如 ARM 与 x86)上编译和运行,将返回不同的结果.

You need to be careful, however, as unsafe code is, well, unsafe. After the slice::from_raw_parts_mut() invocation, there exist two mutable handles to the same data at the same time, which is a violation of Rust aliasing rules. Therefore you would want to keep the mutable slice created out of a structure for the shortest possible time. I also assume that you know about endianness issues - the code above is by no means portable, and will return different results if compiled and run on different kinds of machines (ARM vs x86, for example).

如果您可以选择格式并且想要紧凑的二进制格式,请考虑使用 bincode.否则,如果您需要,例如要解析一些预定义的二进制结构,byteorder crate 是要走的路.

If you can choose the format and you want a compact binary one, consider using bincode. Otherwise, if you need e.g. to parse some pre-defined binary structure, byteorder crate is the way to go.

这篇关于如何从 Rust 中的文件读取结构?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆