mirror of https://github.com/rust-lang/reference
419 lines
12 KiB
Markdown
419 lines
12 KiB
Markdown
# Paths
|
|
|
|
A *path* is a sequence of one or more path segments _logically_ separated by
|
|
a namespace <span class="parenthetical">qualifier (`::`)</span>. If a path
|
|
consists of only one segment, it refers to either an [item] or a [variable] in
|
|
a local control scope. If a path has multiple segments, it always refers to an
|
|
item.
|
|
|
|
Two examples of simple paths consisting of only identifier segments:
|
|
|
|
<!-- ignore: syntax fragment -->
|
|
```rust,ignore
|
|
x;
|
|
x::y::z;
|
|
```
|
|
|
|
## Types of paths
|
|
|
|
### Simple Paths
|
|
|
|
> **<sup>Syntax</sup>**\
|
|
> _SimplePath_ :\
|
|
> `::`<sup>?</sup> _SimplePathSegment_ (`::` _SimplePathSegment_)<sup>\*</sup>
|
|
>
|
|
> _SimplePathSegment_ :\
|
|
> [IDENTIFIER] | `super` | `self` | `crate` | `$crate`
|
|
|
|
Simple paths are used in [visibility] markers, [attributes], [macros], and [`use`] items.
|
|
Examples:
|
|
|
|
```rust
|
|
use std::io::{self, Write};
|
|
mod m {
|
|
#[clippy::cyclomatic_complexity = "0"]
|
|
pub (in super) fn f1() {}
|
|
}
|
|
```
|
|
|
|
### Paths in expressions
|
|
|
|
> **<sup>Syntax</sup>**\
|
|
> _PathInExpression_ :\
|
|
> `::`<sup>?</sup> _PathExprSegment_ (`::` _PathExprSegment_)<sup>\*</sup>
|
|
>
|
|
> _PathExprSegment_ :\
|
|
> _PathIdentSegment_ (`::` _GenericArgs_)<sup>?</sup>
|
|
>
|
|
> _PathIdentSegment_ :\
|
|
> [IDENTIFIER] | `super` | `self` | `Self` | `crate` | `$crate`
|
|
>
|
|
> _GenericArgs_ :\
|
|
> `<` `>`\
|
|
> | `<` ( _GenericArg_ `,` )<sup>\*</sup> _GenericArg_ `,`<sup>?</sup> `>`
|
|
>
|
|
> _GenericArg_ :\
|
|
> [_Lifetime_] | [_Type_] | _GenericArgsConst_ | _GenericArgsBinding_ | _GenericArgsBounds_
|
|
>
|
|
> _GenericArgsConst_ :\
|
|
> [_BlockExpression_]\
|
|
> | [_LiteralExpression_]\
|
|
> | `-` [_LiteralExpression_]\
|
|
> | [_SimplePathSegment_]
|
|
>
|
|
> _GenericArgsBinding_ :\
|
|
> [IDENTIFIER] _GenericArgs_<sup>?</sup> `=` [_Type_]
|
|
>
|
|
> _GenericArgsBounds_ :\
|
|
> [IDENTIFIER] _GenericArgs_<sup>?</sup> `:` [_TypeParamBounds_]
|
|
|
|
Paths in expressions allow for paths with generic arguments to be specified. They are
|
|
used in various places in [expressions] and [patterns].
|
|
|
|
The `::` token is required before the opening `<` for generic arguments to avoid
|
|
ambiguity with the less-than operator. This is colloquially known as "turbofish" syntax.
|
|
|
|
```rust
|
|
(0..10).collect::<Vec<_>>();
|
|
Vec::<u8>::with_capacity(1024);
|
|
```
|
|
|
|
The order of generic arguments is restricted to lifetime arguments, then type
|
|
arguments, then const arguments, then equality constraints.
|
|
|
|
Const arguments must be surrounded by braces unless they are a
|
|
[literal] or a single segment path.
|
|
|
|
The synthetic type parameters corresponding to `impl Trait` types are implicit,
|
|
and these cannot be explicitly specified.
|
|
|
|
## Qualified paths
|
|
|
|
> **<sup>Syntax</sup>**\
|
|
> _QualifiedPathInExpression_ :\
|
|
> _QualifiedPathType_ (`::` _PathExprSegment_)<sup>+</sup>
|
|
>
|
|
> _QualifiedPathType_ :\
|
|
> `<` [_Type_] (`as` _TypePath_)<sup>?</sup> `>`
|
|
>
|
|
> _QualifiedPathInType_ :\
|
|
> _QualifiedPathType_ (`::` _TypePathSegment_)<sup>+</sup>
|
|
|
|
Fully qualified paths allow for disambiguating the path for [trait implementations] and
|
|
for specifying [canonical paths](#canonical-paths). When used in a type specification, it
|
|
supports using the type syntax specified below.
|
|
|
|
```rust
|
|
struct S;
|
|
impl S {
|
|
fn f() { println!("S"); }
|
|
}
|
|
trait T1 {
|
|
fn f() { println!("T1 f"); }
|
|
}
|
|
impl T1 for S {}
|
|
trait T2 {
|
|
fn f() { println!("T2 f"); }
|
|
}
|
|
impl T2 for S {}
|
|
S::f(); // Calls the inherent impl.
|
|
<S as T1>::f(); // Calls the T1 trait function.
|
|
<S as T2>::f(); // Calls the T2 trait function.
|
|
```
|
|
|
|
### Paths in types
|
|
|
|
> **<sup>Syntax</sup>**\
|
|
> _TypePath_ :\
|
|
> `::`<sup>?</sup> _TypePathSegment_ (`::` _TypePathSegment_)<sup>\*</sup>
|
|
>
|
|
> _TypePathSegment_ :\
|
|
> _PathIdentSegment_ (`::`<sup>?</sup> ([_GenericArgs_] | _TypePathFn_))<sup>?</sup>
|
|
>
|
|
> _TypePathFn_ :\
|
|
> `(` _TypePathFnInputs_<sup>?</sup> `)` (`->` [_TypeNoBounds_])<sup>?</sup>
|
|
>
|
|
> _TypePathFnInputs_ :\
|
|
> [_Type_] (`,` [_Type_])<sup>\*</sup> `,`<sup>?</sup>
|
|
|
|
Type paths are used within type definitions, trait bounds, type parameter bounds,
|
|
and qualified paths.
|
|
|
|
Although the `::` token is allowed before the generics arguments, it is not required
|
|
because there is no ambiguity like there is in _PathInExpression_.
|
|
|
|
```rust
|
|
# mod ops {
|
|
# pub struct Range<T> {f1: T}
|
|
# pub trait Index<T> {}
|
|
# pub struct Example<'a> {f1: &'a i32}
|
|
# }
|
|
# struct S;
|
|
impl ops::Index<ops::Range<usize>> for S { /*...*/ }
|
|
fn i<'a>() -> impl Iterator<Item = ops::Example<'a>> {
|
|
// ...
|
|
# const EXAMPLE: Vec<ops::Example<'static>> = Vec::new();
|
|
# EXAMPLE.into_iter()
|
|
}
|
|
type G = std::boxed::Box<dyn std::ops::FnOnce(isize) -> isize>;
|
|
```
|
|
|
|
## Path qualifiers
|
|
|
|
Paths can be denoted with various leading qualifiers to change the meaning of
|
|
how it is resolved.
|
|
|
|
### `::`
|
|
|
|
Paths starting with `::` are considered to be *global paths* where the segments of the path
|
|
start being resolved from a place which differs based on edition. Each identifier in
|
|
the path must resolve to an item.
|
|
|
|
> **Edition Differences**: In the 2015 Edition, identifiers resolve from the "crate root"
|
|
> (`crate::` in the 2018 edition), which contains a variety of different items, including
|
|
> external crates, default crates such as `std` or `core`, and items in the top level of
|
|
> the crate (including `use` imports).
|
|
>
|
|
> Beginning with the 2018 Edition, paths starting with `::` resolve from
|
|
> crates in the [extern prelude]. That is, they must be followed by the name of a crate.
|
|
|
|
```rust
|
|
pub fn foo() {
|
|
// In the 2018 edition, this accesses `std` via the extern prelude.
|
|
// In the 2015 edition, this accesses `std` via the crate root.
|
|
let now = ::std::time::Instant::now();
|
|
println!("{:?}", now);
|
|
}
|
|
```
|
|
|
|
```rust,edition2015
|
|
// 2015 Edition
|
|
mod a {
|
|
pub fn foo() {}
|
|
}
|
|
mod b {
|
|
pub fn foo() {
|
|
::a::foo(); // call `a`'s foo function
|
|
// In Rust 2018, `::a` would be interpreted as the crate `a`.
|
|
}
|
|
}
|
|
# fn main() {}
|
|
```
|
|
|
|
### `self`
|
|
|
|
`self` resolves the path relative to the current module. `self` can only be used as the
|
|
first segment, without a preceding `::`.
|
|
|
|
In a method body, a path which consists of a single `self` segment resolves to the method's self parameter.
|
|
|
|
|
|
```rust
|
|
fn foo() {}
|
|
fn bar() {
|
|
self::foo();
|
|
}
|
|
struct S(bool);
|
|
impl S {
|
|
fn baz(self) {
|
|
self.0;
|
|
}
|
|
}
|
|
# fn main() {}
|
|
```
|
|
|
|
### `Self`
|
|
|
|
`Self`, with a capital "S", is used to refer to the implementing type within
|
|
[traits] and [implementations].
|
|
|
|
`Self` can only be used as the first segment, without a preceding `::`.
|
|
|
|
```rust
|
|
trait T {
|
|
type Item;
|
|
const C: i32;
|
|
// `Self` will be whatever type that implements `T`.
|
|
fn new() -> Self;
|
|
// `Self::Item` will be the type alias in the implementation.
|
|
fn f(&self) -> Self::Item;
|
|
}
|
|
struct S;
|
|
impl T for S {
|
|
type Item = i32;
|
|
const C: i32 = 9;
|
|
fn new() -> Self { // `Self` is the type `S`.
|
|
S
|
|
}
|
|
fn f(&self) -> Self::Item { // `Self::Item` is the type `i32`.
|
|
Self::C // `Self::C` is the constant value `9`.
|
|
}
|
|
}
|
|
```
|
|
|
|
### `super`
|
|
|
|
`super` in a path resolves to the parent module. It may only be used in leading
|
|
segments of the path, possibly after an initial `self` segment.
|
|
|
|
```rust
|
|
mod a {
|
|
pub fn foo() {}
|
|
}
|
|
mod b {
|
|
pub fn foo() {
|
|
super::a::foo(); // call a's foo function
|
|
}
|
|
}
|
|
# fn main() {}
|
|
```
|
|
|
|
`super` may be repeated several times after the first `super` or `self` to refer to
|
|
ancestor modules.
|
|
|
|
```rust
|
|
mod a {
|
|
fn foo() {}
|
|
|
|
mod b {
|
|
mod c {
|
|
fn foo() {
|
|
super::super::foo(); // call a's foo function
|
|
self::super::super::foo(); // call a's foo function
|
|
}
|
|
}
|
|
}
|
|
}
|
|
# fn main() {}
|
|
```
|
|
|
|
### `crate`
|
|
|
|
`crate` resolves the path relative to the current crate. `crate` can only be used as the
|
|
first segment, without a preceding `::`.
|
|
|
|
```rust
|
|
fn foo() {}
|
|
mod a {
|
|
fn bar() {
|
|
crate::foo();
|
|
}
|
|
}
|
|
# fn main() {}
|
|
```
|
|
|
|
### `$crate`
|
|
|
|
`$crate` is only used within [macro transcribers], and can only be used as the first
|
|
segment, without a preceding `::`. `$crate` will expand to a path to access items from the
|
|
top level of the crate where the macro is defined, regardless of which crate the macro is
|
|
invoked.
|
|
|
|
```rust
|
|
pub fn increment(x: u32) -> u32 {
|
|
x + 1
|
|
}
|
|
|
|
#[macro_export]
|
|
macro_rules! inc {
|
|
($x:expr) => ( $crate::increment($x) )
|
|
}
|
|
# fn main() { }
|
|
```
|
|
|
|
## Canonical paths
|
|
|
|
Items defined in a module or implementation have a *canonical path* that
|
|
corresponds to where within its crate it is defined. All other paths to these
|
|
items are aliases. The canonical path is defined as a *path prefix* appended by
|
|
the path segment the item itself defines.
|
|
|
|
[Implementations] and [use declarations] do not have canonical paths, although
|
|
the items that implementations define do have them. Items defined in
|
|
block expressions do not have canonical paths. Items defined in a module that
|
|
does not have a canonical path do not have a canonical path. Associated items
|
|
defined in an implementation that refers to an item without a canonical path,
|
|
e.g. as the implementing type, the trait being implemented, a type parameter or
|
|
bound on a type parameter, do not have canonical paths.
|
|
|
|
The path prefix for modules is the canonical path to that module. For bare
|
|
implementations, it is the canonical path of the item being implemented
|
|
surrounded by <span class="parenthetical">angle (`<>`)</span> brackets. For
|
|
[trait implementations], it is the canonical path of the item being implemented
|
|
followed by `as` followed by the canonical path to the trait all surrounded in
|
|
<span class="parenthetical">angle (`<>`)</span> brackets.
|
|
|
|
The canonical path is only meaningful within a given crate. There is no global
|
|
namespace across crates; an item's canonical path merely identifies it within
|
|
the crate.
|
|
|
|
```rust
|
|
// Comments show the canonical path of the item.
|
|
|
|
mod a { // crate::a
|
|
pub struct Struct; // crate::a::Struct
|
|
|
|
pub trait Trait { // crate::a::Trait
|
|
fn f(&self); // crate::a::Trait::f
|
|
}
|
|
|
|
impl Trait for Struct {
|
|
fn f(&self) {} // <crate::a::Struct as crate::a::Trait>::f
|
|
}
|
|
|
|
impl Struct {
|
|
fn g(&self) {} // <crate::a::Struct>::g
|
|
}
|
|
}
|
|
|
|
mod without { // crate::without
|
|
fn canonicals() { // crate::without::canonicals
|
|
struct OtherStruct; // None
|
|
|
|
trait OtherTrait { // None
|
|
fn g(&self); // None
|
|
}
|
|
|
|
impl OtherTrait for OtherStruct {
|
|
fn g(&self) {} // None
|
|
}
|
|
|
|
impl OtherTrait for crate::a::Struct {
|
|
fn g(&self) {} // None
|
|
}
|
|
|
|
impl crate::a::Trait for OtherStruct {
|
|
fn f(&self) {} // None
|
|
}
|
|
}
|
|
}
|
|
|
|
# fn main() {}
|
|
```
|
|
|
|
[_BlockExpression_]: expressions/block-expr.md
|
|
[_Expression_]: expressions.md
|
|
[_GenericArgs_]: #paths-in-expressions
|
|
[_Lifetime_]: trait-bounds.md
|
|
[_LiteralExpression_]: expressions/literal-expr.md
|
|
[_SimplePathSegment_]: #simple-paths
|
|
[_Type_]: types.md#type-expressions
|
|
[_TypeNoBounds_]: types.md#type-expressions
|
|
[_TypeParamBounds_]: trait-bounds.md
|
|
[literal]: expressions/literal-expr.md
|
|
[item]: items.md
|
|
[variable]: variables.md
|
|
[implementations]: items/implementations.md
|
|
[use declarations]: items/use-declarations.md
|
|
[IDENTIFIER]: identifiers.md
|
|
[`use`]: items/use-declarations.md
|
|
[attributes]: attributes.md
|
|
[expressions]: expressions.md
|
|
[extern prelude]: names/preludes.md#extern-prelude
|
|
[macro transcribers]: macros-by-example.md
|
|
[macros]: macros-by-example.md
|
|
[patterns]: patterns.md
|
|
[trait implementations]: items/implementations.md#trait-implementations
|
|
[traits]: items/traits.md
|
|
[visibility]: visibility-and-privacy.md
|