C++ 模板函数 - 编译器错误:“无法从 const char* 更改为 int”

问题描述 投票:0回答:3

我指定了一个模板函数:

template<class T> void jsonParse(json_object* jobj, eParseWhat parseWhat, T &value) {
    ...

    if(parseWhat == PARSE_UID) {
        value = json_object_getInt(val);
    }
    if(parseWhar == PARSE_EMAIL) {
        value = json_object_getString(val);
    }
    ...
}

现在,当我想解析 json 对象的

uid
时,我使用
int
:

调用该方法
json_object* obj = ...;
int uid = 0;
jsonParse(obj,PARSE_UID,uid);

但是随后在行中的赋值处发生编译错误:

value = json_object_getString(val);

由于使用

int
进行调用,编译器认为变量
value
的类型是
int
并且
json_object_getString(val)
返回
const char*
。所以编译器说:
can not convert from const char* to int

您有什么建议来解决这个问题吗?

c++ templates
3个回答
1
投票

如果您要为每种类型执行一堆 if 语句的 switch 语句,为什么还要使用模板呢?如果您想将每种类型视为多种类型,您的模板实例化将永远无法编译。这种设计是有缺陷的,但如果你必须的话,你可以使用专业化来完成类似的事情。

template<class T> void jsonParse(json_object* jobj, eParseWhat parseWhat, T &value) {
    static_assert(false); // not a handled type
}

template<> void jsonParse(json_object* jobj, eParseWhat parseWhat, int &value) {
    value = json_object_getInt(val);
}

template<> void jsonParse(json_object* jobj, eParseWhat parseWhat, std::string &value) {
    value = json_object_getString(val);
}

正如 GMan 指出的那样,通常最好重载函数而不是专门化函数模板。使用重载函数的等效效果如下:

void jsonParse(json_object* jobj, eParseWhat parseWhat, int &value) {
        value = json_object_getInt(val);
    }

void jsonParse(json_object* jobj, eParseWhat parseWhat, std::string &value) {
        value = json_object_getString(val);
    }

0
投票

你的代码不会以任何方式编译,因为在该方法中 T 值不能同时是 int 和 char*...

您尝试将不同类型(一个是 int,一个是 char)转换为一个值(甚至没有定义);)

首先你必须使用:

json_object* obj = ...;
int uid = 0;

jsonParse<int>(obj,PARSE_UID,uid); //last parameter is int

jsonParse<string>(obj,PARSE_UID,whatever); //last parameter is string

但这不起作用,正如之前所说...您不能在一个模板中以两种不同的方式使用一种类型...

对不起...:)


0
投票

你不是想写吗:

    if(parseWhat == PARSE_UID) {
        value = json_object_getInt(val);
    }
    else if(parseWhar == PARSE_EMAIL) {
        value = json_object_getString(val);
    }

旁注:您的示例中的模板用法对我来说非常奇怪和令人困惑。我宁愿为此使用某种

Variant
类(一个例子是 boost::any,但您可以轻松实现自己的 - 这只需两个小时)。

© www.soinside.com 2019 - 2024. All rights reserved.