Подтвердить что ты не робот

Как использовать std:: is_volatile?

Я пытаюсь запретить определенную операцию по летучим типам. Для этого я пытаюсь использовать std::is_volatile, но приведенный ниже код компилируется без ошибок, чего я не хочу.

Почему is_volatile::value false в приведенном ниже примере?

#include <type_traits>

template<typename T>
inline void DoStuff(T val) {
    static_assert(!std::is_volatile<T>::value, "No volatile types plz");
    //...
}

int main() {
    volatile char sometext[261];
    DoStuff(sometext);
}
4b9b3361

Ответ 1

Проблема заключается в том, что T не является типом volatile вообще. Это volatile char*. Подождите, вы говорите, я вижу volatile прямо там. Правда, но учтите следующее: char* volatile является изменчивым типом. volatile char* нет. Он является энергонезависимым указателем на энергозависимый массив char.

Решение: std::is_volatile<typename std::remove_pointer<T>::type>

Ответ 2

При попытке передать массив по значению он распадается на указатель на его первый элемент.

Это означает, что val на самом деле a int volatile *. Таким образом, он указывает на volatile int, но сам по себе не является изменчивым. Следовательно, std::is_volatile возвращает false.

Вы можете попробовать взять массив по ссылке или использовать std::remove_pointer.

Ответ 3

Поскольку функции принимают свой аргумент по значению, cv-квалификация исходного аргумента теряется.

Примите его по ссылке:

void DoStuff(T& val)