# Namespaces

A namespace is a logical grouping of declared names. Names are segregated into separate namespaces based on the kind of entity the name refers to. Namespaces allow the occurrence of a name in one namespace to not conflict with the same name in another namespace.

Within a namespace, names are organized in a hierarchy, where each level of the hierarchy has its own collection of named entities.

There are several different namespaces that each contain different kinds of entities. The usage of a name will look for the declaration of that name in different namespaces, based on the context, as described in the name resolution chapter.

The following is a list of namespaces, with their corresponding entities:

- Type Namespace
  - Module declarations
  - External crate declarations
  - External crate prelude items
  - Struct, union, enum, enum variant declarations
  - Trait item declarations
  - Type aliases
  - Associated type declarations
  - Built-in types: boolean, numeric, and textual
  - Generic type parameters
  - `Self` type
  - Tool attribute modules
- Value Namespace
  - Function declarations
  - Constant item declarations
  - Static item declarations
  - Struct constructors
  - Enum variant constructors
  - `Self` constructors
  - Generic const parameters
  - Associated const declarations
  - Associated function declarations
  - Local bindings — `let`, `if let`, `while let`, `for`, `match` arms, function parameters, closure parameters
  - Captured closure variables
- Macro Namespace
  - `macro_rules` declarations
  - Built-in attributes
  - Tool attributes
  - Function-like procedural macros
  - Derive macros
  - Derive macro helpers
  - Attribute macros
- Lifetime Namespace
  - Generic lifetime parameters
- Label Namespace1
  - Loop labels

An example of how overlapping names in different namespaces can be used unambiguously:

    #![allow(unused)]
    fn main() {
    // Foo introduces a type in the type namespace and a constructor in the value
    // namespace.
    struct Foo(u32);

    // The `Foo` macro is declared in the macro namespace.
    macro_rules! Foo {
        () => {};
    }

    // `Foo` in the `f` parameter type refers to `Foo` in the type namespace.
    // `'Foo` introduces a new lifetime in the lifetime namespace.
    fn example<'Foo>(f: Foo) {
        // `Foo` refers to the `Foo` constructor in the value namespace.
        let ctor = Foo;
        // `Foo` refers to the `Foo` macro in the macro namespace.
        Foo!{}
        // `'Foo` introduces a label in the label namespace.
        'Foo: loop {
            // `'Foo` refers to the `'Foo` lifetime parameter, and `Foo`
            // refers to the type namespace.
            let x: &'Foo Foo;
            // `'Foo` refers to the label.
            break 'Foo;
        }
    }
    }

## Named entities without a namespace

The following entities have explicit names, but the names are not a part of any specific namespace.

### Fields

Even though struct, enum, and union fields are named, the named fields do not live in an explicit namespace. They can only be accessed via a field expression, which only inspects the field names of the specific type being accessed.

### Use declarations

A use declaration has named aliases that it imports into scope, but the `use` item itself does not belong to a specific namespace. Instead, it can introduce aliases into multiple namespaces, depending on the item kind being imported.

1

`rustc` currently warns about shadowing when using the same name for a label and lifetime in the same scope, but it still treats them independently. This is intended as a future-compatibility warning about a possible extension to the language. See PR #24162.