什么时候 pub 和 pub(super) 有不同的语义?

问题描述

Rust 支持 pubpub(super)pub 使得父模块可以访问一个项目......而 pub(super) 似乎也做完全相同的事情。我试过玩下面的例子,交换 pubpub(super) 似乎没有效果

#![allow(dead_code)]

mod outer {
    pub(super) fn outer_foo() { inner::inner_foo(); }
    mod inner {
        pub(super) fn inner_foo() { println!("Hello World!"); }
    }
}

fn top_level_foo() { outer::outer_foo(); }

为什么你会使用一个而不是另一个

Playground link.

解决方法

在您的示例中,如果您将 inner 模块更改为公共模块,那么区别就会很明显。

例如,这是有效的,因为 outer::inner::inner_foo 在主模块中是可见的:

#![allow(dead_code)]

mod outer {
    pub(super) fn outer_foo() { inner::inner_foo(); }
    pub mod inner {
        pub fn inner_foo() { println!("hello world!"); }
    }
}

fn top_level_foo() { outer::outer_foo(); }

fn main() {
    outer::inner::inner_foo();
}

如果您将 inner_foo 保留为 pub(super),它只会在 outer 模块中可见(因为 super 指的是超级模块,{{1} } 在 outer 中的东西的情况下),因此上面的代码不会编译,你会看到这个错误:

inner

请注意, | 13 | outer::inner::inner_foo(); | ^^^^^^^^^ private function | note: the function `inner_foo` is defined here 也可以将 pub 作为参数,使该函数在 crate 内公开,但不能在其他 crate 中公开。