简体   繁体   中英

Why doesn't std::remove_const remove const qualifier?

Note that I use std::thread just to get readable types in the errors:

int main() {
    const int * first;
    using deref = decltype(*first);
    std::thread s = std::remove_const<deref>::type{}; // const int ???
    std::thread s2 = deref{}; // const int
    std::thread s3 = std::remove_const<const int>::type{}; // int 
}

It seems as if remove_const<deref>::type is const int , not mutable int as I would expect.

Note that *first is an lvalue expression, then the result type of decltype(*first) would be const int& , ie a reference to const int . The reference is not const itself (it can't be const-qualified, there's no such thing like int& const ), using std::remove_const on it will yield the same type, ie const int& .

See decltype specifier :

  1. If the argument is any other expression of type T , and

b) if the value category of expression is lvalue, then decltype yields T& ;

You could use std::remove_const with std::remove_reference together:

std::remove_const<std::remove_reference<deref>::type>::type // -> int
                                        ^^^^^               // -> const int &
                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^        // -> const int

BTW:

Note that I use std::thread just to get readable types in the errors:

Note that it doesn't give the correct type for this case. Here's a class template helper for this from the Effective Modern C++ (Scott Meyers) :

template<typename T>
class TD;

and use it as

TD<deref> td;

You'll get the error message containing the type of deref , eg from clang :

prog.cc:16:11: error: implicit instantiation of undefined template 'TD<const int &>'
TD<deref> td;
          ^

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM