C++ 从C+;中的模板函数返回字符串和整数+;
我正在尝试使用模板编写一个通用函数,它能够返回bool、integer、char*或stringC++ 从C+;中的模板函数返回字符串和整数+;,c++,templates,if-statement,C++,Templates,If Statement,我正在尝试使用模板编写一个通用函数,它能够返回bool、integer、char*或string template<typename entryType> entryType getEntry(xml_node node, const char* entryKey) { ... if (is_same<entryType, bool>::value) { return boolvalue; //returning a boolean
template<typename entryType>
entryType getEntry(xml_node node, const char* entryKey)
{
...
if (is_same<entryType, bool>::value) {
return boolvalue; //returning a boolean
}
else if(is_same<entryType, int>::value) {
return a; //this is an integer
}
else if (is_same<entryType, char*>::value) {
return result; //this is a char*
}
}
模板
entryType getEntry(xml_节点,常量字符*entryKey)
{
...
如果(相同::值){
return boolvalue;//返回布尔值
}
else if(相同::值){
返回一个;//这是一个整数
}
else if(相同::值){
返回结果;//这是一个字符*
}
}
我想可以这样称呼它:
bool bPublisher = getEntry<bool>(node, "Publisher");
int QoS = getEntry<int>(node, "QualityOfService");
char* sBrokerUrl = getEntry<char*>(node, "BrokerUrl");
boolbPublisher=getEntry(节点,“发布者”);
intQoS=getEntry(节点,“QualityOfService”);
char*sBrokerUrl=getEntry(节点,“BrokerUrl”);
作为char*的替代方法,字符串也可以:
string sBrokerUrl = getEntry<string>(node, "BrokerUrl");
string sBrokerUrl=getEntry(节点,“BrokerUrl”);
我会遇到如下错误:无法从'bool'转换为'char*'。我理解这个问题,编译器无法检测代码执行分支是否依赖于我给出的类型。我就是找不到解决办法。有人能帮我吗?谢谢。因为C++17可以使用;其条件部分将在编译时进行计算,如果结果为true
,则语句false部分(否则为语句true部分)将被丢弃。(因此不会导致错误)
如果constexpr(相同::值){
return boolvalue;//返回布尔值
}
如果constexpr(相同::值){
返回一个;//这是一个整数
}
如果constexpr(相同::值){
返回结果;//这是一个字符*
}
< P>对于C++的旧版本,可以通过转发到通过引用传递的参数返回结果的重载函数来解决这个问题:
template<typename entryType>
entryType getEntry(xml_node node, const char* entryKey)
{
entryType result = entryType();
this->getEntry(node, entryKey, result);
return result;
}
void getEntry(xml_node node, const char* entryKey, bool& result);
void getEntry(xml_node node, const char* entryKey, int& result);
void getEntry(xml_node node, const char* entryKey, char const *& result);
但第一个解决方案,IMO,更具可读性。如果不想公开重载函数,可以将其设置为私有函数。如@tobi303在评论中所说,应该专门化模板。 不需要花哨的斯菲娜或其他把戏
#include <iostream>
#include <type_traits>
using namespace std;
template<typename entryType>
entryType getEntry(const char* entryKey);
template <>
int getEntry<int>(const char* entryKey)
{
return 1;
}
template <>
bool getEntry<bool>(const char* entryKey)
{
return false;
}
template <>
string getEntry<string>(const char* entryKey)
{
return "asd";
}
int main() {
bool bPublisher = getEntry<bool>("Publisher");
int QoS = getEntry<int>("QualityOfService");
string sBrokerUrl = getEntry<string>("BrokerUrl");
cout << bPublisher << '\n' << QoS << '\n'<< sBrokerUrl << '\n';
}
#包括
#包括
使用名称空间std;
模板
entryType getEntry(常量字符*entryKey);
模板
int getEntry(const char*entryKey)
{
返回1;
}
模板
bool getEntry(const char*entryKey)
{
返回false;
}
模板
字符串getEntry(常量字符*entryKey)
{
返回“asd”;
}
int main(){
bool bPublisher=getEntry(“发布者”);
intQoS=getEntry(“QualityOfService”);
字符串sBrokerUrl=getEntry(“BrokerUrl”);
我想我会倾向于利用std::tuple
已经非常出色的功能
将其与标记的值相结合,就有可能以最小的工作量为这类事情生成富有表现力的、类型安全的代码
#include <iostream>
#include <tuple>
template<class Tag, class Type>
struct xmlvalue : Type
{
using Type::Type;
};
template<class Tag> struct xmlvalue<Tag, bool>
{
xmlvalue(bool v) : value_(v) {}
operator bool&() { return value_; }
operator bool const&() const { return value_; }
private:
bool value_;
};
template<class Tag> struct xmlvalue<Tag, int>
{
xmlvalue(int v) : value_(v) {}
operator int&() { return value_; }
operator int const&() const { return value_; }
private:
int value_;
};
struct is_publisher_tag {};
struct qos_tag {};
struct broker_url_tag {};
using is_publisher = xmlvalue<is_publisher_tag, bool>;
using qos = xmlvalue<qos_tag, int>;
using broker_url = xmlvalue<broker_url_tag, std::string>;
struct quote : std::tuple<is_publisher , qos, broker_url >
{
using std::tuple<is_publisher , qos, broker_url >::tuple;
};
int main() {
auto q1 = quote(true, 100, "http:://foo.com");
auto q2 = quote(false, 50, "http:://bar.com");
std::cout << std::get<broker_url>(q1) << ", " << std::get<qos>(q1) << ", " << std::get<is_publisher>(q1) << std::endl;
std::cout << std::get<broker_url>(q2) << ", " << std::get<qos>(q2) << ", " << std::get<is_publisher>(q2) << std::endl;
return 0;
}
如果您无法使用C++17,则模板专门化可能会满足您的要求:
template<typename entryType>
entryType getEntry(xml_node node, const char* entryKey) {}
template<>
bool getEntry<bool>(xml_node node, const char* entryKey) {
return true;
}
template<>
int getEntry<int>(xml_node node, const char* entryKey) {
return 1;
}
模板
entryType getEntry(xml_节点,const char*entryKey){}
模板
bool getEntry(xml_节点,const char*entryKey){
返回true;
}
模板
int getEntry(xml_节点,const char*entryKey){
返回1;
}
您可以将任何共享代码放入从每个专门化调用的助手函数中:
void shared_code(xml_node node, const char* entryKey) {
// ...
}
template<>
bool getEntry<bool>(xml_node node, const char* entryKey) {
shared_code(node, entryKey);
return true;
}
template<>
int getEntry<int>(xml_node node, const char* entryKey) {
shared_code(node, entryKey);
return 1;
}
void共享\u代码(xml\u节点,const char*entryKey){
// ...
}
模板
bool getEntry(xml_节点,const char*entryKey){
共享_代码(节点、入口键);
返回true;
}
模板
int getEntry(xml_节点,const char*entryKey){
共享_代码(节点、入口键);
返回1;
}
好吧,你不能用一个普通的if
-statement来实现这一点。你不能依赖于运行时if语句的返回类型。你需要专门化你的模板。毕竟,一旦编译了tempalte,它就变成了一个普通函数,你可以使用一个定义良好的返回类型。我正要发布这个:|@P0W关于FGITWC++17解决方案的所有内容在接下来的10年里,离子在现实生活中几乎毫无用处years@lightnessracesinorbit那么C++11解决方案在2021年会有用吗?@RickAstley:希望如此!现实世界的工业发展非常缓慢,因为它依赖于稳定性、安全性和安全性。除非你需要,否则你不会改变技术,因为有人可能会因此无故死亡。
http:://foo.com, 100, 1
http:://bar.com, 50, 0
template<typename entryType>
entryType getEntry(xml_node node, const char* entryKey) {}
template<>
bool getEntry<bool>(xml_node node, const char* entryKey) {
return true;
}
template<>
int getEntry<int>(xml_node node, const char* entryKey) {
return 1;
}
void shared_code(xml_node node, const char* entryKey) {
// ...
}
template<>
bool getEntry<bool>(xml_node node, const char* entryKey) {
shared_code(node, entryKey);
return true;
}
template<>
int getEntry<int>(xml_node node, const char* entryKey) {
shared_code(node, entryKey);
return 1;
}