c++ 如何正确编写一个返回类型为void的模板 Package 响应类

wgx48brx  于 2023-11-19  发布在  其他
关注(0)|答案(2)|浏览(98)

我想写一个调用函数的 Package 器类,

  • 如果函数成功退出,则将结果存储在 Package 器的data字段中
  • 否则,将异常转换为int错误代码。

这是我得到的:

struct ResponseBase
{
    int code = 0;
};

template<typename T>
struct Response : ResponseBase
{
    T data;
};

template<>
struct Response<void> : ResponseBase {
};

template<typename F>
auto try_catch_wrapper(F&& f)
{
    Response<decltype(f())> res;
    try
    {
        res.data = f(); // here's the problem
    }
    catch (const std::exception&)
    {
        res.code = -1;
    }
    return res;
}

int main() {
    auto a = try_catch_wrapper([]() {
        return 1;
        });

    if (a.code == 0)
    {
        std::cout << "Invoke Success, Result: " << a.data << std::endl;
    }
    else
    {
        std::cout << "Error occured! Code: " << a.code << std::endl;
    }

    // won't work for void return type
    //auto b = try_catch_wrapper([]() {
    //    return;
    //    });
}

字符串

eqfvzcg8

eqfvzcg81#

我只想调用f()
您可以使用constexpr,如果如下所示:

template<typename F>
auto try_catch_wrapper(F&& f)
{
    Response<decltype(f())> res;
    try
    { 
        //added this constexpr if
        if constexpr(!std::is_same_v<decltype(f()), void>)
        {
                res.data = f();
        }
        else
        {
            f();
        }
        
    }
    catch (const std::exception&)
    {
        res.code = -1;
    }
    return res;
}

字符串
Demo

tzxcd3kk

tzxcd3kk2#

一个C++14版本将有2个SFINAE重载:

template<typename F,
         std::enable_if_t<std::is_same<decltype(std::declval<F>()()), void>::value, bool> = false>
auto try_catch_wrapper(F&& f)
{
    Response<decltype(f())> res;
    try
    { 
        f();
    }
    catch (const std::exception&)
    {
        res.code = -1;
    }
    return res;
}

template<typename F,
         std::enable_if_t<!std::is_same<decltype(std::declval<F>()()), void>::value, bool> = false>
auto try_catch_wrapper(F&& f)
{
    Response<decltype(f())> res;
    try
    { 
        res.data = f(); // here's the problem
    }
    catch (const std::exception&)
    {
        res.code = -1;
    }
    return res;
}

字符串
Demo

相关问题