打印!宏按顺序执行

Sar*_*ner 2 rust rust-macros

我的部分代码如下所示:

print_usage_instructions();
print!("Command: ");
let stdin = io::stdin();
let mut line = String::new();
stdin.lock().read_line(&mut line).expect("Couldn't process the command.");
println!("{}", line);
Run Code Online (Sandbox Code Playgroud)

我期望的行为是这样的:

Usage instructions and stuff
Command: [my command]
[my command]
Run Code Online (Sandbox Code Playgroud)

但是,会发生什么:

Usage instructions and stuff
[my command]
Command: [my command]
Run Code Online (Sandbox Code Playgroud)

任何想法为什么会发生?AFAIK,编译器没有理由在这里更改执行顺序,这部分代码不是异步也不是多线程.

Luk*_*odt 7

问题:print!()不刷新标准输出!

你问,冲洗意味着什么?打印时,你不希望自己将每个字符发送到stdout:这会产生很多开销(想想:做一个系统调用,终端必须更新它的视图,......).因此,不是这样做,而是存在一个缓冲区,其中包含即将打印的内容.要实际打印,必须刷新此缓冲区.

你几乎没有注意到所有这一切的原因是,当'\n'打印换行符()时,stdout总是被刷新.因此,println!()总是冲洗!

您的用例更令人困惑,因为您正在键入stdin.它的工作方式大致相同:当您键入时,字符尚未发送到任何地方!只有终端/ shell存储您输入的内容.但是一旦你按下enter(换行符),你的书面文字就会被提交并发送给stdin.

无论如何,你可以手动刷新标准输出而不打印换行符:

use std::io::{self, BufRead, Write};

fn main() {
    println!("Usage instructions and stuff");

    print!("Command:");
    io::stdout().flush().expect("Couldn't flush stdout");   // <-- here

    let stdin = io::stdin();
    let mut line = String::new();
    stdin.lock().read_line(&mut line).expect("Couldn't process the command.");
    println!("{}", line);
}
Run Code Online (Sandbox Code Playgroud)

这种行为之前受到批评:" print!应该冲洗stdout".


请注意:您的字符串最后line包含换行符.你可以删除它trim_right().这与你原来的问题无关,但你也可能遇到这个问题;-)