【问题标题】:c++11 segmentation fault while playing with variadic templates使用可变参数模板时出现c ++ 11分段错误
【发布时间】:2017-03-09 20:46:43
【问题描述】:

所以我在玩 c++11 Varidiacs,我想创建一个叫做 CallClass 的东西,基本上是一个扭曲函数的类,以便以后调用,当所有变量都设置好时(真的我不知道如果它可能有用):

#include <tuple>

template <typename OBJ,typename F,typename... VARGS>
class CallClass
{
    public:

        CallClass(OBJ& object,F callFunction)
        :_object(&object),_func(callFunction)
        { }

        CallClass(const CallClass& other)
        :_func_args(other._func_args)
        ,_object(other._object)
        ,_func(other._func)
        { }

        template <size_t INDEX>
        auto get(){ return std::get<INDEX>(_func_args); }

        template <size_t INDEX,typename T>
        void set(const T& val){ std::get<INDEX>(_func_args) = val; }

        template <size_t INDEX,typename T>
        void set(T&& val){ std::get<INDEX>(_func_args) = val; }

        auto Call()
        {
            //throws segmentation Fault Here
            return InnerCall<0>(_func_args);
        }

        virtual ~CallClass() {}

    protected:

    private:
        std::tuple<VARGS...> _func_args;
        OBJ* _object;
        F _func;

        template <size_t INDEX,typename... ARGS>
        auto InnerCall(std::tuple<VARGS...>& tup,ARGS... args)
        {
            auto arg = std::get<INDEX>(tup);

            return InnerCall<INDEX + 1>(tup,args...,arg);
        }

        template <size_t INDEX,VARGS...>
        auto InnerCall(std::tuple<VARGS...>& tup,VARGS... args)
        {
            return (_object->*_func)(args...);
        }
};

现在当我尝试编译(使用 IDE:code::blocks 编译,配置为在 windows 上使用 MINGW)时,它会打印 Compiler:Segmentation Fault,任何人有任何想法吗?

用法:

class obj{
public:
    obj(int a)
    :_a(a)
    { }

    virtual ~obj() {}

    int add(int b,int c){
        return _a + b + c;
    }

private:
    int _a;
};

int main(){
obj ob(6);
CallClass<obj,decltype(obj::add),int,int> callAdd(ob,obj::add);

    callAdd.set<0,int>(5);
    callAdd.set<1,int>(7);
    cout << "result is " << callAdd.Call() << endl;

    return 0;
}

【问题讨论】:

  • 这首先不能编译:(

标签: c++11 mingw variadic-templates g++4.9


【解决方案1】:

经过一番搜索,我偶然发现了一个类似的问题,在某种程度上。 显然我解包元组的方式是一个问题,所以我决定使用不同的方法,如下所示:enter link description here

必须添加一些更改以满足我的需要:

变化:

namespace detail
{
    template <typename OBJ,typename F, typename Tuple, bool Done, int Total, int... N>
    struct call_impl
    {
        static auto call(OBJ& obj,F f, Tuple && t)
        {
            return call_impl<OBJ,F, Tuple, Total == 1 + sizeof...(N), Total, N..., sizeof...(N)>::call(obj,f, std::forward<Tuple>(t));
        }
    };

    template <typename OBJ,typename F, typename Tuple, int Total, int... N>
    struct call_impl<OBJ,F, Tuple, true, Total, N...>
    {
        static auto call(OBJ& obj,F f, Tuple && t)
        {
            return (obj.*f)(std::get<N>(std::forward<Tuple>(t))...);
        }
    };
}

// user invokes this
template <typename OBJ,typename F, typename Tuple>
auto call(OBJ& obj,F f, Tuple && t)
{
    typedef typename std::decay<Tuple>::type ttype;
    return detail::call_impl<OBJ,F, Tuple, 0 == std::tuple_size<ttype>::value, std::tuple_size<ttype>::value>::call(obj,f, std::forward<Tuple>(t));
}

并更改了 Call():

auto Call()
{
    std::tuple<VARGS...> func_args = _func_args;
    return call(*_object,_func, std::move(func_args));
}

我可能会再做一些更改,比如将元组作为引用传递,并使结构成为我的类的一部分。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-14
    • 1970-01-01
    • 2015-11-10
    • 1970-01-01
    • 2021-02-17
    相关资源
    最近更新 更多