为什么Rust在主函数中没有返回值,以及如何返回值



在Rust中main函数是这样定义的:

fn main() {
}

这个函数不允许返回值。为什么一种语言不允许返回值,是否有一种方法可以返回一些东西?我是否能够安全地使用c exit(int)函数,或者这会导致泄漏和其他什么?

从Rust 1.26开始,main可以返回一个Result:

use std::fs::File;
fn main() -> Result<(), std::io::Error> {
    let f = File::open("bar.txt")?;
    Ok(())
}

在这种情况下,如果出现错误,返回的错误码是1。如果使用File::open("bar.txt").expect("file not found");,则返回错误值101(至少在我的机器上)。

同样,如果你想返回一个更通用的错误,使用:

use std::error::Error;
...
fn main() -> Result<(), Box<dyn Error>> {
   ...
}

这不再是使用状态退出的推荐方式,请参阅关于从main返回和实现Termination的类型的其他答案


std::process::exit(code: i32)是用代码退出的方式。


Rust这样做是为了有一个一致的显式接口从程序返回值,无论它是从哪里设置的。如果main启动了一系列任务,那么这些任务中的任何一个都可以设置返回值,即使main已经退出。

Rust确实有一种方法来编写一个返回值的main函数,但是它通常在stdlib中抽象。有关详细信息,请参阅关于编写不使用stdlib的可执行文件的文档。

如函数文档中所述,这将立即退出而不运行任何析构函数,因此应谨慎使用:

注意,因为这个函数永远不会返回,并且它会终止进程,所以不会运行当前堆栈或任何其他线程堆栈上的析构函数。如果需要彻底关闭,建议只在没有更多析构函数可运行的情况下调用此函数。

正如其他人所指出的,std::process::exit(code: i32)是这里的方法

关于原因的更多信息在RFC 1011:进程退出中给出。关于RFC的讨论在RFC的pull request中

关于这个的reddit帖子有一个"为什么";解释:

Rust当然可以设计成这样。事实上,过去是这样的。

但是由于Rust使用的任务模型,fn主任务可以启动一堆其他任务,然后退出!但是其中一个任务可能想要在main退出后设置操作系统退出代码。

调用set_exit_status是显式的,简单的,并且当你不关心的时候,不需要你总是在main的底部放一个0。

尝试:

use std::process::ExitCode;
fn main() -> ExitCode {
  ExitCode::from(2)
}

看一下doc

或:

use std::process::{ExitCode, Termination};
pub enum LinuxExitCode { E_OK, E_ERR(u8) }
impl Termination for LinuxExitCode {
   fn report(self) -> ExitCode {
     match self {
       LinuxExitCode::E_OK => ExitCode::SUCCESS,
       LinuxExitCode::E_ERR(v) => ExitCode::from(v)
     }
   }
}
fn main() -> LinuxExitCode {
    LinuxExitCode::E_ERR(3)
}

您可以使用std::os::set_exit_status设置返回值

相关内容

  • 没有找到相关文章

最新更新