A type, const or lifetime parameter that is specified for `impl` is not
constrained.

Erroneous code example:

```compile_fail,E0207
struct Foo;

impl<T: Default> Foo {
    // error: the type parameter `T` is not constrained by the impl trait, self
    // type, or predicates [E0207]
    fn get(&self) -> T {
        <T as Default>::default()
    }
}
```

Any type or const parameter of an `impl` must meet at least one of the
following criteria:

 - it appears in the _implementing type_ of the impl, e.g. `impl<T> Foo<T>`
 - for a trait impl, it appears in the _implemented trait_, e.g.
   `impl<T> SomeTrait<T> for Foo`
 - it is bound as an associated type, e.g. `impl<T, U> SomeTrait for T
   where T: AnotherTrait<AssocType=U>`

Any unconstrained lifetime parameter of an `impl` is not supported if the
lifetime parameter is used by an associated type.

### Error example 1

Suppose we have a struct `Foo` and we would like to define some methods for it.
The previous code example has a definition which leads to a compiler error:

The problem is that the parameter `T` does not appear in the implementing type
(`Foo`) of the impl. In this case, we can fix the error by moving the type
parameter from the `impl` to the method `get`:

```
struct Foo;

// Move the type parameter from the impl to the method
impl Foo {
    fn get<T: Default>(&self) -> T {
        <T as Default>::default()
    }
}
```

### Error example 2

As another example, suppose we have a `Maker` trait and want to establish a
type `FooMaker` that makes `Foo`s:

```compile_fail,E0207
trait Maker {
    type Item;
    fn make(&mut self) -> Self::Item;
}

struct Foo<T> {
    foo: T
}

struct FooMaker;

impl<T: Default> Maker for FooMaker {
// error: the type parameter `T` is not constrained by the impl trait, self
// type, or predicates [E0207]
    type Item = Foo<T>;

    fn make(&mut self) -> Foo<T> {
        Foo { foo: <T as Default>::default() }
    }
}
```

This fails to compile because `T` does not appear in the trait or in the
implementing type.

One way to work around this is to introduce a phantom type parameter into
`FooMaker`, like so:

```
use std::marker::PhantomData;

trait Maker {
    type Item;
    fn make(&mut self) -> Self::Item;
}

struct Foo<T> {
    foo: T
}

// Add a type parameter to `FooMaker`
struct FooMaker<T> {
    phantom: PhantomData<T>,
}

impl<T: Default> Maker for FooMaker<T> {
    type Item = Foo<T>;

    fn make(&mut self) -> Foo<T> {
        Foo {
            foo: <T as Default>::default(),
        }
    }
}
```

Another way is to do away with the associated type in `Maker` and use an input
type parameter instead:

```
// Use a type parameter instead of an associated type here
trait Maker<Item> {
    fn make(&mut self) -> Item;
}

struct Foo<T> {
    foo: T
}

struct FooMaker;

impl<T: Default> Maker<Foo<T>> for FooMaker {
    fn make(&mut self) -> Foo<T> {
        Foo { foo: <T as Default>::default() }
    }
}
```

### Error example 3

Suppose we have a struct `Foo` and we would like to define some methods for it.
The following code example has a definition which leads to a compiler error:

```compile_fail,E0207
struct Foo;

impl<const T: i32> Foo {
    // error: the const parameter `T` is not constrained by the impl trait, self
    // type, or predicates [E0207]
    fn get(&self) -> i32 {
        i32::default()
    }
}
```

The problem is that the const parameter `T` does not appear in the implementing
type (`Foo`) of the impl. In this case, we can fix the error by moving the type
parameter from the `impl` to the method `get`:


```
struct Foo;

// Move the const parameter from the impl to the method
impl Foo {
    fn get<const T: i32>(&self) -> i32 {
        i32::default()
    }
}
```

### Error example 4

Suppose we have a struct `Foo` and a struct `Bar` that uses lifetime `'a`. We
would like to implement trait `Contains` for `Foo`. The trait `Contains` have
the associated type `B`. The following code example has a definition which
leads to a compiler error:

```compile_fail,E0207
struct Foo;
struct Bar<'a>;

trait Contains {
    type B;

    fn get(&self) -> i32;
}

impl<'a> Contains for Foo {
    type B = Bar<'a>;

    // error: the lifetime parameter `'a` is not constrained by the impl trait,
    // self type, or predicates [E0207]
    fn get(&self) -> i32 {
        i32::default()
    }
}
```

Please note that unconstrained lifetime parameters are not supported if they are
being used by an associated type.

### Additional information

For more information, please see [RFC 447].

[RFC 447]: https://github.com/rust-lang/rfcs/blob/master/text/0447-no-unused-impl-parameters.md
