如何在编译期间检查 Rust 中设置的功能?

dra*_*r40 7 rust rust-cargo

我正在尝试使用 Rusts 功能有条件地编译我的板条箱中的模块,并且仅在启用功能时才使用它。当设置该功能时,条件编译工作正常,但在未设置该功能时拒绝编译。

我使用相同的功能标志有条件地导入主模块中的模块,因此我的假设是,当不使用该功能时不应导入该模块。

#[cfg(feature = "debug")]
pub mod k {
    pub struct S { pub x: i32, pub y: i32}
}
Run Code Online (Sandbox Code Playgroud)

以及我如何在 main 中使用它

pub fn main() {
    if cfg!(feature = "debug") {
        use self::k;
        let _s = k::S {x: 4, y: 5};
    }

    let g = vec![1, 2, 4];
    println!("{:?}", g);
}
Run Code Online (Sandbox Code Playgroud)

如果我通过标志启用该功能,--features那么它会按预期进行编译:

#[cfg(feature = "debug")]
pub mod k {
    pub struct S { pub x: i32, pub y: i32}
}
Run Code Online (Sandbox Code Playgroud)

但是,当我没有通过时,--features它会失败,我的期望是它应该跳过带有该cfg!集合的块。

pub fn main() {
    if cfg!(feature = "debug") {
        use self::k;
        let _s = k::S {x: 4, y: 5};
    }

    let g = vec![1, 2, 4];
    println!("{:?}", g);
}
Run Code Online (Sandbox Code Playgroud)

这就是我的Cargo.toml样子

[features]
default = []
debug = []
Run Code Online (Sandbox Code Playgroud)

有人可以解释为什么会发生这种情况以及有条件编译此类代码块的更好方法吗?

ale*_*der 2

我在评论中看到您已经找到了解决方案。

但是如果您想根据功能标志创建一个变量怎么办?

这是我的想法:

#[cfg(feature = "debug")]
pub mod k {
    pub struct S { pub x: i32, pub y: i32}
}

pub fn main() {
    #[cfg(feature = "debug")]
    let variable = {
        use self::k;
        let _s = k::S {x: 4, y: 5};
        // this is now a struct
        _s
    };

    #[cfg(not(feature = "debug"))]
    let variable = {
        // this is now a string
        String::from("same variable; \
        different data types depending on feature flags")
        
    };

    println!("conditional compilation is cool:\n{:?}", variable);
}
Run Code Online (Sandbox Code Playgroud)

playground

基本上,就像是cfg!(feature = "debug")。不同的是,宏内部的东西cfg!必须在编译时有效,这意味着数据类型或方法必须存在于当前范围内才能被调用。

cfg!因此,例如,您不能使用在 -if 语句内条件编译的结构。