Paths

A path is a sequence of one or more path components logically separated by namespace qualifiers (::). If a path consists of only one component, it may refer to either an item or a variable in a local control scope. If a path has multiple components, it refers to an item.

Every item has a canonical path within its crate, but the path naming an item 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.

Two examples of simple paths consisting of only identifier components:

x;
x::y::z;

Path components are usually identifiers, but they may also include angle-bracket-enclosed lists of type arguments. In expression context, the type argument list is given after a :: namespace qualifier in order to disambiguate it from a relational expression involving the less-than symbol (<). In type expression context, the final namespace qualifier is omitted.

Two examples of paths with type arguments:


# #![allow(unused_variables)]
#fn main() {
# struct HashMap<K, V>(K,V);
# fn f() {
# fn id<T>(t: T) -> T { t }
type T = HashMap<i32,String>; // Type arguments used in a type expression
let x  = id::<i32>(10);       // Type arguments used in a call expression
# }
#}

Types of paths

Simple paths

Syntax
SimplePath :
   ::? PathSegmentIdentifier (:: PathSegmentIdentifier)*

PathSegmentIdentifier :
   IDENTIFIER | super | self | Self FIXME

Simple paths are used on pub markers, macro invocations and use items.

Paths in expressions

Syntax
PathInExpr :
   ::? PathSegmentIdentifier (:: (PathSegmentIdentifier | GenericsForType) )*

QualifiedPathInExpr :
   < type_ (as TypePath)? > :: PathInExpr

Paths in types

Syntax
TypePath :
   ::? TypePathElement (:: TypePathElement)*

TypePathElement :
   PathSegmentIdentifier (GenericsForType | FunctionSignature)?

GenericsForType :
      < (LifetimeParams (, TypeParamsForTypes)? (, BindingParams)? ,? )? >
   | < TypeParamsForTypes (, BindingParams)? ,? >
   | < BindingParams ,? >

TypeParamsForTypes :
   Type (, Type)*

BindingParams :
   TypeBindingParam (, TypeBindingParam)*

TypeBindingParam :
   IDENTIFIER = type_ FIXME

Canonical paths

Qualified paths

Syntax
Qualified_TypePath_ :
   < Type (as TypePath)? > :: TypePath FIXME

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 component 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 angle (<>) 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 angle (<>) 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.

// Comments show the canonical path of the item.

mod a { // ::a
    pub struct Struct; // ::a::Struct

    pub trait Trait { // ::a::Trait
        fn f(&self); // a::Trait::f
    }

    impl Trait for Struct {
        fn f(&self) {} // <::a::Struct as ::a::Trait>::f
    }

    impl Struct {
        fn g(&self) {} // <::a::Struct>::g
    }
}

mod without { // ::without
    fn canonicals() { // ::without::canonicals
        struct OtherStruct; // None

        trait OtherTrait { // None
            fn g(&self); // None
        }

        impl OtherTrait for OtherStruct {
            fn g(&self) {} // None
        }

        impl OtherTrait for ::a::Struct {
            fn g(&self) {} // None
        }

        impl ::a::Trait for OtherStruct {
            fn f(&self) {} // None
        }
    }
}

# fn main() {}