跨多个文件/模块拆分实现,并尽可能保持私有

时间:2016-03-15 20:38:15

标签: module rust private public

考虑我的库中的以下代码:

pub struct Foo;
impl Foo {
    fn helper(&self) { /* .. */ }
}

pub fn do_something(foo: &Foo) {
    foo.helper();
}

我的图书馆用户应该能够使用Foodo_something(),但永远不会致电helper()。使用上面的代码一切正常。但现在想象代码变得庞大,我想将这些定义分成他们自己的文件/模块 - 然后用pub use将它们拉回到根命名空间。见这里:

mod foo {  // module contents in `src/foo.rs`
    pub struct Foo;
    impl Foo {
        fn helper(&self) { /* .. */ }
    }    
}

mod do_something {  // module contents in `src/do_something.rs`
    use super::Foo;
    pub fn do_something(foo: &Foo) {
        foo.helper();
    }
}

pub use foo::Foo;
pub use do_something::do_something;

现在编译器抱怨helper()是私有的。确实如此,但我仍然希望do_something()能够使用它。但我不希望我的用户使用它。我怎么能这样做?

我尝试过的解决方案归结为“如何访问兄弟模块的私有项目?”。所以回答这个问题对我有帮助。但是提供替代解决方案/解决方案也会很棒!

2 个答案:

答案 0 :(得分:4)

假设货物项目的文件结构如下:

src\lib.rs
src\foo\mod.rs
src\foo\do_something.rs
src\bin\test.rs

test.rs只是为了证明它适用于图书馆的用户。

在src \ lib.rs中:

mod foo;

pub use foo::*;

在src \ foo \ mod.rs中:

mod do_something;

pub use self::do_something::*;

pub struct Foo;

impl Foo {
    fn helper(&self) { /* .. */ }
}

在src \ foo \ do_something.rs中:

use super::Foo;
pub fn do_something(foo: &Foo) {
    foo.helper();
}

在src \ bin \ test.rs

extern crate mylibname;
use mylibname::*;

fn main() {
    let foo = Foo;
    do_something(&foo);
    // foo.helper(); //Uncommenting gives an error.
}

这为我编译。

答案 1 :(得分:3)

Rust 1.18开始,您可以使用pub(crate)语法在整个包中展示某些内容但不在其外部:

mod foo {  // module contents in `src/foo.rs`
    pub struct Foo;
    impl Foo {
        pub(crate) fn helper(&self) { /* .. */ }
    }    
}

编译器建议的所有可能性包括:

  • pub(crate):仅在当前包装箱中可见
  • pub(super):仅在当前模块的父级
  • 中可见
  • pub(in path::to::module):仅在指定路径上可见