Two *template-id*s refer to the same
class, function, or variable if

- their corresponding type
*template-argument*s are the same type and - their corresponding non-type template arguments of integral or enumeration type have identical values and
- their corresponding non-type
*template-argument*s of pointer type refer to the same object or function or are both the null pointer value and - their corresponding non-type
*template-argument*s of pointer-to-member type refer to the same class member or are both the null member pointer value and - their corresponding non-type
*template-argument*s of reference type refer to the same object or function and - their corresponding template
*template-argument*s refer to the same template.

[ Example

: *end example*

]```
template<class E, int size> class buffer { /* ... */ };
buffer<char,2*512> x;
buffer<char,1024> y;
```

declares
x
and
y
to be of the same type, and

```
template<class T, void(*err_fct)()> class list { /* ... */ };
list<int,&error_handler1> x1;
list<int,&error_handler2> x2;
list<int,&error_handler2> x3;
list<char,&error_handler2> x4;
```

template<class T> struct X { }; template<class> struct Y { }; template<class T> using Z = Y<T>; X<Y<int> > y; X<Z<int> > z;—

Two such *decltype-specifier*s
refer to the same type only if their *expression*s are
equivalent ([temp.over.link]).