[meta.rqmts]

# 21 Metaprogramming library [[meta]](./#meta)

## 21.3 Metaprogramming and type traits [[type.traits]](type.traits#meta.rqmts)

### 21.3.2 Requirements [meta.rqmts]

[1](#1)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/meta.tex#L94)

A *Cpp17UnaryTypeTrait* describes a property
of a type[.](#1.sentence-1)

It shall be a class template that takes one template type
argument and, optionally, additional arguments that help define the
property being described[.](#1.sentence-2)

It shall be [*Cpp17DefaultConstructible*](utility.arg.requirements#:Cpp17DefaultConstructible "16.4.4.2 Template argument requirements [utility.arg.requirements]"),[*Cpp17CopyConstructible*](utility.arg.requirements#:Cpp17CopyConstructible "16.4.4.2 Template argument requirements [utility.arg.requirements]"),
and publicly and unambiguously derived, directly or indirectly, from
its [*base characteristic*](#def:base_characteristic "21.3.2 Requirements [meta.rqmts]"), which is
a specialization of the template[integral_constant](meta.help#lib:integral_constant "21.3.4 Helper classes [meta.help]"), with
the arguments to the template integral_constant determined by the
requirements for the particular property being described[.](#1.sentence-3)

The member names of the base characteristic shall not be hidden and shall be
unambiguously available in the *Cpp17UnaryTypeTrait*[.](#1.sentence-4)

[2](#2)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/meta.tex#L109)

A *Cpp17BinaryTypeTrait* describes a
relationship between two types[.](#2.sentence-1)

It shall be a class template that
takes two template type arguments and, optionally, additional
arguments that help define the relationship being described[.](#2.sentence-2)

It shall
be [*Cpp17DefaultConstructible*](utility.arg.requirements#:Cpp17DefaultConstructible "16.4.4.2 Template argument requirements [utility.arg.requirements]"), [*Cpp17CopyConstructible*](utility.arg.requirements#:Cpp17CopyConstructible "16.4.4.2 Template argument requirements [utility.arg.requirements]"),
and publicly and unambiguously derived, directly or
indirectly, from
its [*base characteristic*](#def:base_characteristic), which is a specialization
of the template[integral_constant](meta.help#lib:integral_constant "21.3.4 Helper classes [meta.help]"), with
the arguments to the template integral_constant determined by the
requirements for the particular relationship being described[.](#2.sentence-3)

The member names of the base characteristic shall not be hidden and shall be
unambiguously available in the *Cpp17BinaryTypeTrait*[.](#2.sentence-4)

[3](#3)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/meta.tex#L125)

A *Cpp17TransformationTrait* modifies a property
of a type[.](#3.sentence-1)

It shall be a class template that takes one
template type argument and, optionally, additional arguments that help
define the modification[.](#3.sentence-2)

It shall define a publicly accessible nested type
named type, which shall be a synonym for the modified type[.](#3.sentence-3)

[4](#4)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/meta.tex#L133)

Unless otherwise specified,
the behavior of a program that adds specializations
for any of the templates specified in [[type.traits]](type.traits "21.3 Metaprogramming and type traits") is undefined[.](#4.sentence-1)

[5](#5)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/meta.tex#L139)

Unless otherwise specified, an incomplete type may be used
to instantiate a template specified in [[type.traits]](type.traits "21.3 Metaprogramming and type traits")[.](#5.sentence-1)

The behavior of a program is undefined if

- [(5.1)](#5.1)

an instantiation of a template specified in [[type.traits]](type.traits "21.3 Metaprogramming and type traits") directly or indirectly depends on
 an incompletely-defined object type T, and

- [(5.2)](#5.2)

that instantiation could yield a different result
 were T hypothetically completed[.](#5.sentence-2)
