This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of New status.

### 3423. `std::any_cast` should never return a cv-qualified type

Section: 20.8.5 [any.nonmembers] Status: New Submitter: Casey Carter Opened: 2020-04-02 Last modified: 2020-09-06

Priority: 3

View other active issues in [any.nonmembers].

View all other issues in [any.nonmembers].

View all issues with New status.

Discussion:

The return type of the non-pointer overloads of `std::any_cast<T>` is `T`. This is silly when `T` is cv-qualified (and, since merging P1152 "Deprecating volatile" into the working draft, deprecated when `T` is `volatile`-qualified). We should strip cv-qualifiers to determine the type returned.

[2020-04-18 Issue Prioritization]

Priority to 3 after reflector discussion.

Proposed resolution:

This wording is relative to N4861.

1. Modify 20.8.2 [any.synop] as indicated:

   >     […]
   >     template<class T>
   >       remove_cv_t<T> any_cast(const any& operand);
   >     template<class T>
   >       remove_cv_t<T> any_cast(any& operand);
   >     template<class T>
   >       remove_cv_t<T> any_cast(any&& operand);
   >     […]

2. Modify 20.8.5 [any.nonmembers] as indicated:

   >     template<class T>
   >       remove_cv_t<T> any_cast(const any& operand);
   >     template<class T>
   >       remove_cv_t<T> any_cast(any& operand);
   >     template<class T>
   >       remove_cv_t<T> any_cast(any&& operand);

   > > -4- Let `R` be the type `remove_cv_t<T>`, and `U` be the type `remove_cvref_t<T>`.

   > > -5- Mandates: For the first overload, `is_constructible_v<TR, const U&>` is `true`. For the second overload, `is_constructible_v<TR, U&>` is `true`. For the third overload, `is_constructible_v<TR, U>` is `true`.

   > > -6- Returns: For the first and second overload, `static_cast<TR>(*any_cast<U>(&operand))`. For the third overload, `static_cast<TR>(std::move(*any_cast<U>(&operand)))`.

   > > -7- Throws: `bad_any_cast` if `operand.type() != typeid(remove_reference_t<T>)`.