C++ 模板成员函数无法自动推断类型

C++ 模板成员函数无法自动推断类型,c++,function,class,templates,overloading,C++,Function,Class,Templates,Overloading,我想做的是让函数根据输入返回不同的类型。本质上是返回类型的“重载” 我对函数进行了模板化,但它无法自动推断类型,我必须手动输入所需的类型 #include <iostream> using namespace std; struct S { template<typename T> T Get(int type) { if (type == 0) { return 4; } else if (t

我想做的是让函数根据输入返回不同的类型。本质上是返回类型的“重载”

我对函数进行了模板化,但它无法自动推断类型,我必须手动输入所需的类型

#include <iostream>

using namespace std;

struct S {

    template<typename T>
    T Get(int type) {
        if (type == 0) {
            return 4;
        } else if (type == 1) {
            return true;
        } else {
            return -1;
        }
    };

};

int main() {
    cout << boolalpha;

    S s;
    
    // ok
    int x = s.Get<int>(0); // return an integer
    bool y = s.Get<bool>(1); // return a boolean
    
    // ERROR
    // the end goal is something like this
    // is there a better way to handle this?
    int a = s.Get(0);
    bool b = s.Get(1);

    cout << "x: " << x << '\n'; // “x: 4”
    cout << "y: " << y << '\n'; // “y: true”

}

对于您的最终目标,您可能需要一些模板专门化。类似这样的方法可能会奏效:

template<unsigned S>
struct getHelp; // A helper to help us switch on the number, to get the type.

template<>
struct getHelp<0> { // If our number is 0, we have int type with value 4.
    constexpr static int value = 4;
};

template<>
struct getHelp<1> { // If our number is 1, we have bool type value true.
    constexpr static bool value = true;
};

template<unsigned S>  // We have our function, it overloads the return type based
                      // on that that of the return type of our helper.
constexpr auto get() -> decltype(getHelp<S>::value) {
    return getHelp<S>::value;
}
用途如下:

auto a = get<1>();
注意:如果您的目的是让指示您的类型的数字是动态的,即由用户传入,那么您试图做的是不可能的。C++是一种静态类型的语言,最好的方法是使用具有所有可能类型的STD::
对于您的最终目标,您可能需要一些模板专门化。类似这样的方法可能会奏效:

template<unsigned S>
struct getHelp; // A helper to help us switch on the number, to get the type.

template<>
struct getHelp<0> { // If our number is 0, we have int type with value 4.
    constexpr static int value = 4;
};

template<>
struct getHelp<1> { // If our number is 1, we have bool type value true.
    constexpr static bool value = true;
};

template<unsigned S>  // We have our function, it overloads the return type based
                      // on that that of the return type of our helper.
constexpr auto get() -> decltype(getHelp<S>::value) {
    return getHelp<S>::value;
}
用途如下:

auto a = get<1>();
注意:如果您的目的是让指示您的类型的数字是动态的,即由用户传入,那么您试图做的是不可能的。C++是一种静态类型的语言,最好的方法是使用具有所有可能类型的STD::
如果您有C++17,则可以使用If constexpr,如下所示:

struct S {

    template<int type>
    auto Get() {
        if constexpr (type == 0) {
            return 4;
        }
        else if constexpr (type == 1) {
            return true;
        }
        else {
            return -1;
        }
    };

};
S s;

int x = s.Get<0>(); // return an integer
bool y = s.Get<1>(); // return a boolean
这是一个例子


请注意,类型值必须在编译时已知。在C++中,在运行时,不能赋予返回不同类型的函数。您必须使用std::variant或std::any来执行此操作。

如果您有C++17,则可以使用If constexpr,如下所示:

struct S {

    template<int type>
    auto Get() {
        if constexpr (type == 0) {
            return 4;
        }
        else if constexpr (type == 1) {
            return true;
        }
        else {
            return -1;
        }
    };

};
S s;

int x = s.Get<0>(); // return an integer
bool y = s.Get<1>(); // return a boolean
这是一个例子


请注意,类型值必须在编译时已知。在C++中,在运行时,不能赋予返回不同类型的函数。您必须使用STD::变体或STD::任何要这样做。

< P>这是不可能的,因为类型必须在编译时知道,C++不支持CONTHEXPR函数参数。即:

// valid
template <int key> 
auto fun() { if constexpr (key==0) return true; }

// unsupported
auto fun(constexpr int key)
{ if constexpr (key == 0) return true; }

这是不可能的,因为类型必须在编译时知道,C++不支持CONTXPR函数参数。即:

// valid
template <int key> 
auto fun() { if constexpr (key==0) return true; }

// unsupported
auto fun(constexpr int key)
{ if constexpr (key == 0) return true; }

我使用C++ 17。C++中没有这样的东西,因为它是返回类型上的重载。可以返回一个变体,它本质上是一个类型安全的联合,一次可以包含一个类型。@Peter我已经接近一个有利的结果,问题是调用时不能只使用Get;,为了让它工作,我必须使用Get。我想知道我是否可以得到模板来自动推断类型。@ XkaaAtSu-你认为什么信息在调用某处?特别是如果在调用点,get成员函数已经声明但未定义。我使用C++ 17。C++中没有这样的事情,因为返回类型上有重载。可以返回一个变体,它本质上是一个类型安全的联合,一次可以包含一个类型。@Peter我已经接近一个有利的结果,问题是调用时不能只使用Get;,为了让它工作,我必须使用Get。我想知道我是否可以得到模板来自动推断类型。@ XkaaAtSu-你认为什么信息在调用某处?特别是在调用点,Get成员函数已经声明但没有定义。这是一个非常简洁的c++17答案。对constexpr做得很好,如果有时我忘记了它的存在。这是这里最好的答案。这是一个超级简洁的c++17答案。对constexpr做得很好,如果有时我忘记了它的存在。这是最好的答案。