标准库更多介绍

标准库提供了很多其他类型支持某些功能,如:
线程(Threads)
信道(Channels)
文件输入输出(File I/O)

线程

  • Rust通过spawn函数提供了创建本地操作系统的机制,该函数参数是通过值捕获变量的闭包
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
use std::thread;

static NTHREADS: i32 = 10;

// 这是主(`main`)线程
fn main() {
// 提供一个 vector 来存放所创建的子线程(children)。
let mut children = vec![];

for i in 0..NTHREADS {
// 启动(spin up)另一个线程
children.push(thread::spawn(move || {
println!("this is thread number {}", i)
}));
}

for child in children {
// 等待线程结束。返回一个结果。
let _ = child.join();
}
}

测试实例:map-reduce

  • Rust提供可以直接使用的线程类型。主要有XOR、Mutex、Channel这三种类型。

通道

  • Rust为线程之间通信提供了异步的通道,通道允许两个端点之间信息单向流动:Sender(发送端)和Receiver(接收端)

路径

  • Path结构体代表了底层文件系统的文件路径。分为两种:
    类Unix系统: posix::Path
    windows系统: windows:Path
  • Path在内部不是以UTF-8字符串表示,而是以若干字节vec这样的vector表示,所以将Path转换为&str是有消耗的,并且可能失败,因此将其定义为一个Option

文件输入输出(I/O)

  • I/O在进行文件输入输出时可能会产生错误,因此File的所有方法均返回io::Result类型,这是Result<T,io::Error>的别名。

打开文件open

  • open静态方法以只读模式打开文件
  • File会在自身被drop时关闭文件。

创建文件create

  • create以只写模式打开文件,如果文件存在,旧的内容会被销毁,否则创建一个新的文件。
  • 还有其他方法类似read+write,在Rust标准库中可以查找到。

读取行

  • 该文件必须在当前路径之中
  • 处理大文件的时候对比String更加有效。

子进程

  • process::Output表示已经结束的子进程
  • process::Command表示是一个进程的创建者

这些命令相当于是在命令行输入对应的命令。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
use std::process::Command;

fn main() {
let output = Command::new("rustc")
.arg("--version")
.output().unwrap_or_else(|e| {
panic!("failed to execute process: {}", e)
});

if output.status.success() {
let s = String::from_utf8_lossy(&output.stdout);

print!("rustc succeeded and stdout was:\n{}", s);
} else {
let s = String::from_utf8_lossy(&output.stderr);

print!("rustc failed and stderr was:\n{}", s);
}
}

管道

  • 首先创建管道,接着写入管道,最后查看stdout的字段,必须解包,因为字段拥有Option类型。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
use std::io::prelude::*;
use std::process::{Command, Stdio};

static PANGRAM: &'static str =
"the quick brown fox jumped over the lazy dog\n";

fn main() {
// 启动 `wc` 命令
let process = match Command::new("wc")
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.spawn() {
Err(why) => panic!("couldn't spawn wc: {:?}", why),
Ok(process) => process,
};

// 将字符串写入 `wc` 的 `stdin`。
//
// `stdin` 拥有 `Option<ChildStdin>` 类型,不过我们已经知道这个实例不为空值,
// 因而可以直接 `unwrap 它。
match process.stdin.unwrap().write_all(PANGRAM.as_bytes()) {
Err(why) => panic!("couldn't write to wc stdin: {:?}", why),
Ok(_) => println!("sent pangram to wc"),
}

// 因为 `stdin` 在上面调用后就不再存活,所以它被 `drop` 了,管道也被关闭。
//
// 这点非常重要,因为否则 `wc` 就不会开始处理我们刚刚发送的输入。

// `stdout` 字段也拥有 `Option<ChildStdout>` 类型,所以必需解包。
let mut s = String::new();
match process.stdout.unwrap().read_to_string(&mut s) {
Err(why) => panic!("couldn't read wc stdout: {:?}", why),
Ok(_) => print!("wc responded with:\n{}", s),
}
}

等待

  • 调用Child::wait就可以等待process::Child完成,会返回一个process::ExitStatus
1
2
3
4
5
6
7
8
9
use std::process::Command;

fn main() {
let mut child = Command::new("sleep").arg("5").spawn().unwrap();
let _result = child.wait().unwrap();

println!("reached end of main");
}

程序参数

  • 命令行参数使用std::env::args进行接收,返回一个迭代器,对每个参数举出一个字符串。使用模式匹配匹配对应的字符串,如果正确,就执行。

外部语言函数接口

  • Rust提供了调用C语言的函数接口。