From dad849809bafdf58b53933780fe3d797ae1ef34e Mon Sep 17 00:00:00 2001 From: Casey Carter Date: Mon, 17 Jul 2017 21:01:07 -0700 Subject: [PATCH] Apply P0547R2 Fixes #70, #229, #300, #301, #310, #313, #339, #381, #382, #387, #399. --- concepts.tex | 144 +++++++++++++++++++++----------------------------- iterators.tex | 23 ++++---- 2 files changed, 72 insertions(+), 95 deletions(-) diff --git a/concepts.tex b/concepts.tex index 7fa4c71d..1aa48581 100644 --- a/concepts.tex +++ b/concepts.tex @@ -480,30 +480,39 @@ \begin{itemdecl} template concept bool Assignable = - CommonReference && requires(T&& t, U&& u) { - { std::forward(t) = std::forward(u) } -> Same; + is_lvalue_reference::value && // \seebelow + CommonReference< + const remove_reference_t&, + const remove_reference_t&> && + requires(T t, U&& u) { + { t = std::forward(u) } -> Same&&; }; \end{itemdecl} \begin{itemdescr} \pnum -Let \tcode{t} be an lvalue of type \tcode{T}, and \tcode{R} be the -type \tcode{remove_reference_t}. If \tcode{U} is an lvalue reference -type, let \tcode{v} be an lvalue of type \tcode{R}; -otherwise, let \tcode{v} be an rvalue of type \tcode{R}. -Let \tcode{uu} be a distinct object of type \tcode{R} such that -\tcode{uu} is equal to \tcode{v}. -\tcode{Assignable} is satisfied only if +Let \tcode{t} be an lvalue which refers to an object \tcode{o} such that +\tcode{decltype((t))} is \tcode{T}, and \tcode{u} an expression such that +\tcode{decltype((u))} is \tcode{U}. Let \tcode{u2} be a distinct object that is +equal to \tcode{u}. \tcode{Assignable} is satisfied only if \begin{itemize} -\item \tcode{addressof(t = v) == addressof(t)}. -\item After evaluating \tcode{t = v}, \tcode{t} is equal to \tcode{uu} and: +\item \tcode{addressof(t = u) == addressof(o)}. + +\item After evaluating \tcode{t = u}, \tcode{t} is equal to \tcode{u2} and: + \begin{itemize} -\item If \tcode{v} is a non-\tcode{const} rvalue, its resulting -state is valid but unspecified~(\cxxref{lib.types.movedfrom}). -\item Otherwise, \tcode{v} is not modified. +\item If \tcode{u} is a non-\tcode{const} xvalue, the resulting state of the +object to which it refers is valid but unspecified~(\cxxref{lib.types.movedfrom}). + +\item Otherwise, if \tcode{u} is a glvalue, the object to which it refers is not +modified. \end{itemize} \end{itemize} + +\pnum +There need not be any subsumption relationship between \tcode{Assignable} +and \tcode{is_lvalue_reference::value}. \end{itemdescr} \rSec2[concepts.lib.corelang.swappable]{Concept \tcode{Swappable}} @@ -818,38 +827,19 @@ \rSec2[concepts.lib.object.destructible]{Concept \tcode{Destructible}} \pnum -The \tcode{Destructible} concept is the base of the hierarchy of object concepts. -It specifies properties that all such object types have in common. +The \tcode{Destructible} concept specifies properties of all types, instances of +which can be destroyed at the end of their lifetime, or reference types. \indexlibrary{\idxcode{Destructible}}% \begin{itemdecl} template -concept bool Destructible = - requires(T t, const T ct, T* p) { - { t.@$\sim$@T() } noexcept; - { &t } -> Same; // not required to be equality preserving - { &ct } -> Same; // not required to be equality preserving - delete p; - delete[] p; - }; +concept bool Destructible = is_nothrow_destructible::value; // \seebelow \end{itemdecl} \begin{itemdescr} \pnum -The expression requirement \tcode{\&ct} does not require implicit expression -variations~(\ref{concepts.lib.general.equality}). - -\pnum -Given a (possibly \tcode{const}) lvalue \tcode{t} of type \tcode{T} and pointer -\tcode{p} of type \tcode{T*}, \tcode{Destructible} is satisfied only if - -\begin{itemize} -\item After evaluating the expression \tcode{t.$\sim$T()}, -\tcode{delete p}, or \tcode{delete[] p}, all resources owned by -the denoted object(s) are reclaimed. -\item \tcode{\&t == addressof(t)}. -\item The expression \tcode{\&t} is non-modifying. -\end{itemize} +There need not be any subsumption relationship between \tcode{Destructible} +and \tcode{is_nothrow_destructible::value}. \pnum \enternote Unlike the \tcode{Destructible} library concept in the \Cpp @@ -860,72 +850,53 @@ \rSec2[concepts.lib.object.constructible]{Concept \tcode{Constructible}} \pnum -The \tcode{Constructible} concept is used to constrain the type of a -variable to be either an object type constructible from a given set of argument -types, or a reference type that can be bound to those arguments. +The \tcode{Constructible} concept constrains the initialization of a variable of +a type with a given set of argument types. \indexlibrary{\idxcode{Constructible}}% \begin{itemdecl} -template -concept bool @\xname{ConstructibleObject}@ = // \expos - Destructible && requires(Args&&... args) { - T{std::forward(args)...}; // not required to be equality preserving - new T{std::forward(args)...}; // not required to be equality preserving - }; - -template -concept bool @\xname{BindableReference}@ = // \expos - is_reference::value && requires(Args&&... args) { - T(std::forward(args)...); - }; - template concept bool Constructible = - @\xname{ConstructibleObject}@ || - @\xname{BindableReference}@; + Destructible && is_constructible::value; // \seebelow \end{itemdecl} +\begin{itemdescr} +\pnum +There need not be any subsumption relationship between \tcode{Constructible} +and \tcode{is_constructible::value}. +\end{itemdescr} + \rSec2[concepts.lib.object.defaultconstructible]{Concept \tcode{DefaultConstructible}} \indexlibrary{\idxcode{DefaultConstructible}}% \begin{itemdecl} template -concept bool DefaultConstructible = - Constructible && - requires(const size_t n) { - new T[n]{}; // not required to be equality preserving - }; +concept bool DefaultConstructible = Constructible; \end{itemdecl} -\pnum -\enternote The array allocation expression \tcode{new T[n]\{\}} implicitly -requires that \tcode{T} has a non-explicit default constructor. \exitnote - \rSec2[concepts.lib.object.moveconstructible]{Concept \tcode{MoveConstructible}} \indexlibrary{\idxcode{MoveConstructible}}% \begin{itemdecl} template concept bool MoveConstructible = - Constructible&&> && - ConvertibleTo&&, T>; + Constructible && ConvertibleTo; \end{itemdecl} \begin{itemdescr} \pnum -Let \tcode{U} be the type \tcode{remove_cv_t}, -\tcode{rv} be an rvalue of type \tcode{U}, -and \tcode{u2} be a distinct object of type \tcode{T} equal to \tcode{rv}. +If \tcode{T} is an object type, then let \tcode{rv} be an rvalue of type \tcode{T} +and \tcode{u2} a distinct object of type \tcode{T} equal to \tcode{rv}. \tcode{MoveConstructible} is satisfied only if \begin{itemize} \item After the definition \tcode{T u = rv;}, \tcode{u} is equal to \tcode{u2}. -\item \tcode{T\{rv\}} or \tcode{*new T\{rv\}} is equal to \tcode{u2}. -\end{itemize} -\pnum -\tcode{rv}'s resulting state is valid but unspecified~(\cxxref{lib.types.movedfrom}). +\item \tcode{T\{rv\}} is equal to \tcode{u2}. +\item If \tcode{T} is not \tcode{const}, \tcode{rv}'s resulting state is valid +but unspecified~(\cxxref{lib.types.movedfrom}); otherwise, it is unchanged. +\end{itemize} \end{itemdescr} \rSec2[concepts.lib.object.copyconstructible]{Concept \tcode{CopyConstructible}} @@ -935,23 +906,21 @@ template concept bool CopyConstructible = MoveConstructible && - Constructible&> && - ConvertibleTo&, T> && - ConvertibleTo&, T> && - ConvertibleTo&&, T>; + Constructible && ConvertibleTo && + Constructible && ConvertibleTo && + Constructible && ConvertibleTo; \end{itemdecl} \begin{itemdescr} \pnum -Let \tcode{v} be an lvalue of type (possibly \tcode{const}) -\tcode{remove_cv_t} or an rvalue of type \tcode{const remove_cv_t}. +If \tcode{T} is an object type, then let \tcode{v} be an lvalue of type (possibly +\tcode{const}) \tcode{T} or an rvalue of type \tcode{const T}. \tcode{CopyConstructible} is satisfied only if \begin{itemize} -\item After the definition \tcode{T u = v;}, \tcode{u} is equal -to \tcode{v}. -\item \tcode{T\{v\}} or \tcode{*new T\{v\}} is equal -to \tcode{v}. +\item After the definition \tcode{T u = v;}, \tcode{u} is equal to \tcode{v}. + +\item \tcode{T\{v\}} is equal to \tcode{v}. \end{itemize} \end{itemdescr} @@ -962,11 +931,18 @@ \begin{itemdecl} template concept bool Movable = + is_object::value && MoveConstructible && Assignable && Swappable; \end{itemdecl} +\begin{itemdescr} +\pnum +There need not be any subsumption relationship between \tcode{Movable} and +\tcode{is_object::value}. +\end{itemdescr} + \rSec2[concepts.lib.object.copyable]{Concept \tcode{Copyable}} \indexlibrary{\idxcode{Copyable}}% diff --git a/iterators.tex b/iterators.tex index 33ab8698..95cb0c79 100644 --- a/iterators.tex +++ b/iterators.tex @@ -965,17 +965,14 @@ \begin{codeblock} template concept bool Readable = - Movable && DefaultConstructible && - requires(const In& i) { + requires { typename value_type_t; typename reference_t; typename rvalue_reference_t; - { *i } -> Same>; - { ranges::iter_move(i) } -> Same>; } && - CommonReference, value_type_t&> && - CommonReference, rvalue_reference_t> && - CommonReference, const value_type_t&>; + CommonReference&&, value_type_t&> && + CommonReference&&, rvalue_reference_t&&> && + CommonReference&&, const value_type_t&>; \end{codeblock} \rSec2[iterators.writable]{Concept \tcode{Writable}} @@ -988,9 +985,13 @@ \begin{codeblock} template concept bool Writable = - Movable && DefaultConstructible && - requires(Out o, T&& t) { + requires(Out&& o, T&& t) { *o = std::forward(t); // not required to be equality preserving + *std::forward(o) = std::forward(t); // not required to be equality preserving + const_cast&&>(*o) = + std::forward(t); // not required to be equality preserving + const_cast&&>(*std::forward(o)) = + std::forward(t); // not required to be equality preserving }; \end{codeblock} @@ -1000,12 +1001,12 @@ \begin{itemize} \item If \tcode{Readable \&\& Same, decay_t{>}} is satisfied, -then \tcode{*o} after the assignment is equal +then \tcode{*o} after any above assignment is equal to the value of \tcode{E} before the assignment. \end{itemize} \pnum -After evaluating the assignment expression, \tcode{o} is not required to be dereferenceable. +After evaluating any above assignment expression, \tcode{o} is not required to be dereferenceable. \pnum If \tcode{E} is an xvalue~(\cxxref{basic.lval}), the resulting