在Rust 1.6中稳定核心库后,以下内容成为可能,我不再需要用libcore
替换libstd
:
//extern crate core; //won't work without this line
extern crate num;
use core::ops::Add;
use num::bigint::{BigInt};
fn main() {
let mut big = "8705702225074732811211966512111".parse::<BigInt>().unwrap();
let one = "1".parse::<BigInt>().unwrap();
big = big.add(&one);
println!("{:?}", big);
}
但有一件事困扰着我 - 为什么我需要申报&#34; extern crate core;&#34;?据我所知,libstd
意在建立在libcore
之上。 libcore
旨在独立于操作系统,而libstd
的实现可能是特定于操作系统的。我从来没有必要指定&#34; extern crate std&#34;。令我困惑的是,在上述情况下,我不需要在Cargo.toml中添加libcore
作为依赖项,尽管它是一个外部箱子。
libcore
是唯一这样的案例吗?当语言的实现变得稳定时,这是暂时的吗?
答案 0 :(得分:8)
事实上,一切都以非常合理的方式运作。
首先,libstd
箱子确实很特别。 Rust编译器知道它并且它隐式地注入extern crate std;
,除非crate root上存在#![no_std]
属性。此外,它还会在您的箱子的每个模块中导入标准前奏曲(再次,除非#![no_std]
存在)。
现在您可以看到为什么在不需要指定extern crate core;
的同时指定extern crate std;
的原因。您也不需要在core
中指定Cargo.toml
,因为libcore
以及其他几个库(libcollections
,liballoc
,{{1}您可以在Rust编译器发行版中找到最新的列表in Rust source directory)。事实上,希望允许通过Cargo提供这些库(以RFC的形式表示),但截至目前,这些库仅提供编译器分发。
最后,请记住Rust的箱子是独立的。 Rust ABI以这样的方式设计,因此您可以在最终的可执行文件中内置相同的crate的不同版本。虽然一个箱子直接依赖同一个箱子的多个版本是无效的,但它的依赖关系可能传递上依赖于另一个箱子的不同版本。这就是为什么你总是必须明确指定你的箱子的依赖性的原因之一:如果你没有指定你的箱子取决于liblibc
,即使libcore
确实取决于{{1}如果libstd
使用libcore
,libcore
将自动被您的包裹拉出。