C++ 检查变量是否为常量

C++ 检查变量是否为常量,c++,c++11,constants,C++,C++11,Constants,我正在读有关康斯特卡斯特的书,它似乎不安全,也没有什么帮助。在这样的情况下,它将非常有用: void func(const char* param, bool modify){ if(modify) //const_cast and change param // stuff that do not change param } 尽管这是一个可能的用法,但它也有风险,因为您必须正确提供“modify”的值,否则您将得到一个未定义的行为,因为您正在更改本应为常量的

我正在读有关康斯特卡斯特的书,它似乎不安全,也没有什么帮助。在这样的情况下,它将非常有用:

void func(const char* param, bool modify){
    if(modify)
        //const_cast and change param
    // stuff that do not change param
}
尽管这是一个可能的用法,但它也有风险,因为您必须正确提供“modify”的值,否则您将得到一个未定义的行为,因为您正在更改本应为常量的内容。我想知道您是否可以在不提供这个额外参数的情况下实现相同的功能,为此,您很可能需要检查const限定符的存在

我发现的是std函数,但它似乎仅限于另一种用法:

is_const<const int>::value //returns true
is_const<int>::value // returns false
const int myVar=1;
is_const<myVar>::value // what it would look like ( does not compile)
is_const::value//返回true
is_const::value//返回false
常量int myVar=1;
is_const::value//它的外观(不编译)

我还尝试过使用类似的函数签名,这些签名只因“const”限定符不同,但这被认为是一种重新定义。那么,有可能做到这一点吗?如果是这样,怎么做?

您可以使用
std::is_const::value
检查
myVar
是否已声明为
const


但是,如果
myVar
是指向另一个对象的指针或引用,则无法从函数内部知道该对象是否为
const

对于这种情况,我认为您可以使用函数的两个重载:

#include <stdio.h>

void func(const char* param) {
    printf("Not modifying %c\n", param[0]);
}

void func(char* param) {
    printf("Modifying %c\n", param[0]);
    func(const_cast<const char*>(param));
}

int main() {
    const char foo[1] = {'F'};
    char bar[1] = {'B'};

    func(foo);
    func(bar);
}
调用
func
时,会根据参数的常量自动选择正确的重载。在这里,我让非常量版本调用常量版本来完成工作的非常量部分,这似乎符合原始用例,但您当然也可以让这两个版本调用第三个(可能是私有/静态)版本,该版本采用原始建议的
bool modify
参数,但现在我们知道常数是正确的)

或者,如果要使用
std::is_const
,可以使用模板函数自动生成常量和非常量的版本,并自动扣除修改参数:

#include <stdio.h>
#include <type_traits>

static void func(char* param, bool modify) {
    if (modify)
        printf("Modifying %c\n", param[0]);
    printf("Not modifying %c\n", param[0]);
}

template<typename T>
void func(T *param) {
    func(const_cast<char*>(param), !std::is_const<T>::value);
}
#包括
#包括
静态无效函数(字符*参数,布尔修改){
如果(修改)
printf(“修改%c\n”,参数[0]);
printf(“未修改%c\n”,参数[0]);
}
模板
无效函数(T*参数){
func(const_cast(param),!std::is_const::value);
}

使用与第一个示例相同的
main()
,这会产生与第一个示例完全相同的输出。

A
remove\u reference\t
有时也很有用。我不确定OP是否理解它的正确用法。在所提供的示例中,这对OP没有任何帮助:)@SergeyA I虽然问题是关于打电话者的方面,但我确实误解了。但是没有办法知道
const
指针或引用是否从内部指向实际的
const
对象…@Quentin,我相信,这就是OP所要问的。@guivenca你需要使用
std::remove_pointer\t
来处理这个问题:指针是非
const
,它的指针是
const
。我认为问题的关键是避免维护一个函数的两个版本。至少这是我要找的。
#include <stdio.h>
#include <type_traits>

static void func(char* param, bool modify) {
    if (modify)
        printf("Modifying %c\n", param[0]);
    printf("Not modifying %c\n", param[0]);
}

template<typename T>
void func(T *param) {
    func(const_cast<char*>(param), !std::is_const<T>::value);
}