# Rust 读写文件
最近因为在研究数据持久化,因此整理了下 Rust 的常见的几种io操作。
>环境:
>edition = "2021"
>rustc 1.60.0-nightly (e789f3a3a 2022-02-11)
>cargo 1.60.0-nightly (c08264864 2022-02-08)
## 按行读取
```rust
use std::fs::File;
use std::io::{BufReader, BufRead};
use std::path::Path;
fn main() {
let path = Path::new("abc.txt");
let file = BufReader::new(File::open(&path).unwrap());
for line in file.lines() {
let line = line.unwrap();
println!("{}", line);
}
}
```
## 按字节读取
u8 无符号8位表示一字节,范围 0-255 。
如 09azAZ 输出 `[48, 57, 97, 122, 65, 90]` ,`\n` 为`[13, 10]`,英文 `,` 为44,中文 `,`为`[239, 188, 140]`。
```rust
fn main() {
let data = std::fs::read("abc.txt").expect("failed to read");
println!("{:?}", data);
println!("{}", data.len());
}
```
## 将文件读取为 String
```rust
use std::io::Read;
fn main() {
let mut data = String::new();
let mut f = std::fs::File::open("hello.txt").expect("Fail to open file");
f.read_to_string(&mut data).expect("Failed to read file");
println!("{}", data);
}
```
## 将文件读取为 `Vec`
```rust
use std::io::Read;
fn main() {
let mut data = Vec::new();
let mut f = std::fs::File::open("hello.txt").expect("Fail to open file");
f.read_to_end(&mut data).expect("Failed to read file");
println!("{:?}", data);
}
```
## String 写入
```rust
fn main() {
let data = "Hello World!";
std::fs::write("hello.txt", data).expect("Failed to write");
}
```
## 字节写入
```rust
use std::fs::File;
use std::io::Write;
fn main() {
let data = "Hello World!";
let mut file = File::create("hello.txt").expect("Failed to create file");
file.write_all(data.as_bytes()).expect("Failed to write to file");
}
```
如果想写入struct Apple ,会报错 the trait bound `Apple: AsRef<[u8]>` is not satisfied. 看起来需要实现 ` AsRef<[u8]>`。然而,还有一种方法是先to_string() 。然后 as_bytes()。例如
```rust
use std::{fs::File, io::Write};
#[derive(Debug)]
struct Apple {
number: i32,
weight: i32,
}
impl std::fmt::Display for Apple {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
write!(f, "Apple number: {} weight{}", self.number, self.weight)
}
}
fn main() {
let data = Apple { number: 1, weight: 2 };
let mut file = File::create("foo.txt").expect("Failed to create file");
file.write_all(data.to_string().as_bytes()).expect("Failed to write to file");
}
```
## 追加写入
说明: 在有该文件时,追加写入。无该文件时,创建文件并写入。
```rust
use std::io::Write;
use std::fs::OpenOptions;
fn main() {
let mut file = OpenOptions::new().create(true).append(true).open("test.txt").expect("Fail to open file");
file.write("append1".as_bytes()).expect("Fail to write append1");
}
```