C ++:无法使用类型条件在模板函数中使用类型为'double'的左值初始化'char *'类型的参数

时间:2017-03-25 15:52:54

标签: c++ arrays templates

我想编写一个模板函数来将数据从一个数组复制到另一个数组。我只想在程序中处理intdoublechar*(字符串)数组。

template<typename T>
void copy_key(T *destination, int destination_index, T *source, int source_index){
    if (typeid(T) == typeid(int) or typeid(T) == typeid(double)){
        destination[destination_index] = source[source_index];
    } else {
        // char* case
        strcpy(destination[destination_index], source[source_index]);
    }
}

如果我如下调用copy_key(),我将收到错误:无法初始化类型为'double'的类型'char *'的参数。

int main(int argc, const char * argv[]) {
    double from_array[3] = {1.0,2.0,3.0};
    double to_array[3];
    copy_key(to_array, 0, from_array, 2);
    std::cout << to_array[0] << std::endl;
    return 0;
}

我想如果Tdouble,则不会输入else块。我的问题是如何在我的示例中正确使用模板类型的条件?

4 个答案:

答案 0 :(得分:5)

  

我想如果Tdouble,则不会输入else块。

你想的没错。但是你对其后果的假设是不正确的。

仅仅因为某些代码不会被执行,并不意味着它与程序的其余部分一起不需要很好地形成。

即使在这种情况下,编译器可能会证明该行不会被执行,但这种证据对于所有可能的程序来说几乎是不可能的,因此它不会影响程序的正确性。

典型的解决方案是使用重载或模板特化:

void copy_key(char *destination, int destination_index, const char *source, int source_index){
    strcpy(...);
}

void copy_key(double *destination, int destination_index, double *source, int source_index){
    destination[destination_index] ...
}

在即将发布的C ++ 17中,将有constexpr if允许在单个函数中有条件地编译块。

答案 1 :(得分:3)

在C ++ 17中,您将得到if constexpr,它只评估if语句的一个分支。

现在,if-part和else-part都必须是类型T的有效代码。如果您希望它对不同类型的行为不同,则必须专门化模板。

答案 2 :(得分:3)

在C ++ 14及之前,使用template specialization代替条件。

C ++是一种编译语言,没有解释。当为特定的具体用途编译模板化函数时,需要编译整个函数,而不仅仅是恰好采用的分支。编译器通常无法推断出代码对所有输入先验所采用的确切路径。

template<typename T>
void copy_key(T *destination, int destination_index, T *source, int source_index){
    destination[destination_index] = source[source_index];
}

template<>
void copy_key(const char** destination, int destination_index, const char** source, int source_index) {
    // char* case
    strcpy(destination[destination_index], source[source_index]);
}

答案 3 :(得分:1)

不,你不能。放作:

template<typename T>
void copy_key(T *destination, int destination_index, T *source, int source_index){
    if (some_condition){ // some_condition met
        destination[destination_index] = source[source_index];
    } else { // some condition not met
        // char* case
        strcpy(destination[destination_index], source[source_index]);
    }
}

更容易看到。

您需要“条件编译”(模板专业化)