Один использует это для отправки вывода на стандартный вывод:
println!("some output")
Я думаю, что нет соответствующего макроса, чтобы сделать то же самое для stderr.
Один использует это для отправки вывода на стандартный вывод:
println!("some output")
Я думаю, что нет соответствующего макроса, чтобы сделать то же самое для stderr.
По Rust 1.19 вы можете использовать eprint
и eprintln
макросы:
fn main() {
eprintln!("This is going to standard error!, {}", "awesome");
}
Первоначально это было предложено в RFC 1896.
Вы можете увидеть реализацию println!
, чтобы погрузиться в то, как это работает, но было немного подавляющим, когда я впервые прочитал его.
Вы можете форматировать материал в stderr, используя похожие макросы, хотя:
use std::io::Write;
let name = "world";
writeln!(&mut std::io::stderr(), "Hello {}!", name);
Это даст вам предупреждение unused result which must be used
, хотя, поскольку печать для ввода-вывода может завершиться неудачно (об этом мы обычно не думаем при печати!). Мы можем видеть, что существующие методы просто паника в этом случае, поэтому мы можем обновить наш код, чтобы сделать то же самое:
use std::io::Write;
let name = "world";
let r = writeln!(&mut std::io::stderr(), "Hello {}!", name);
r.expect("failed printing to stderr");
Это немного, поэтому верните его в макрос:
use std::io::Write;
macro_rules! println_stderr(
($($arg:tt)*) => { {
let r = writeln!(&mut ::std::io::stderr(), $($arg)*);
r.expect("failed printing to stderr");
} }
);
fn main() {
let name = "world";
println_stderr!("Hello {}!", name)
}
print!
и println!
- это удобство методы записи на стандартный вывод. Существуют другие макросы с теми же функциями форматирования, которые доступны для разных задач:
write!
и writeln!
, чтобы написать отформатированная строка в &mut Writer
format!
, чтобы просто сгенерировать отформатированный String
Чтобы записать в стандартный поток ошибок, вы можете использовать, например. writeln!
следующим образом:
use std::io::Write;
fn main() {
let mut stderr = std::io::stderr();
writeln!(&mut stderr, "Error!").unwrap();
}
Сделано так:
use std::io::Write;
fn main() {
std::io::stderr().write(b"some output\n");
}
Вы можете проверить его, отправив вывод программы в /dev/null
, чтобы убедиться, что он работает (я игнорирую предупреждение):
$ rustc foo.rs && ./foo > /dev/null
foo.rs:4:5: 4:42 warning: unused result which must be used, #[warn(unused_must_use)] on by default
foo.rs:4 io::stderr().write(b"some output\n");
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
some output
Аналогично, для stdout можно сделать следующее:
use std::io::Write;
fn main() {
std::io::stdout().write(b"some output\n");
}
Я думаю, что это означает, что println!
- просто удобство: оно короче, а также позволяет некоторое форматирование. В качестве примера последнего отобразится 0x400
:
println!("0x{:x}", 1024u)
Не отвечая на точный вопрос, может быть, интересно, что theres a log
crate, который указывает интерфейс для выровненного ведения журнала, который может выполнять другие ящики (например, env_logger
).
Результат такого ведения журнала будет отправлен на stderr
, и для пользователей есть дополнительные преимущества, такие как указание уровня журнала.
Таким образом, использование такого регистратора может выглядеть так:
#[macro_use]
extern crate log;
extern crate env_logger;
fn main() {
env_logger::init().unwrap();
error!("this is printed by default");
}
(Пример адаптирован из http://burntsushi.net/rustdoc/env_logger/index.html#example)
stderr!("Code {}: Danger, Will Robinson! Danger!", 42);
Другие ответы генерируют неиспользованное предупреждение об импорте с последней ночной, так что вот современный макрос, который Just Works TM.
macro_rules! stderr {
($($arg:tt)*) => (
use std::io::Write;
match writeln!(&mut ::std::io::stderr(), $($arg)* ) {
Ok(_) => {},
Err(x) => panic!("Unable to write to stderr (file handle closed?): {}", x),
}
)
}