Variadic Template C ++中的静态const数组值

时间:2014-05-15 17:51:28

标签: c++ templates c++11 const variadic-templates

我有一个函数,我希望能够运行时检查参数类型,因为我正在将void指针转换回函数。很好奇我如何使用类似

构造的TypeToEnum模板将参数列表转换为哈希值
    #define DEFINE_TYPE(x)\
    template<>\
    struct TypeToEnum<x>\
    {\
      public:\
      static const unsigned int value = HashString(#x);\
    };\

这样我就可以使用模板确定函数签名。我没有 想法如何在invoke方法中将其转换为静态const数组。

    class FunctionDescription
    {
    private:
      int return_type;
      std::vector<int> argument_types;
      std::string m_name;
      void* function;
    public:
const std::string& name() const{ return m_name; }

int ReturnType() const { return return_type; }

const std::vector<int>& arguments() const { return argument_types; }

template<typename Return,typename... Args>
FunctionDescription(const std::string& _name, Return(*func)(Args...)) 
    : m_name(_name), return_type(TypeToEnum<Return>::value)
{
    argument_types = { TypeToEnum<Args>::value... };
    function = func;
}

template<typename Return,typename... Args>
Return invoke(Args... args)
{
    static const int type_check[] = {TypeToEnum<Return>::value,TypeToEnum<std::forward<Args>>::value};

    if (type_check[0] != return_type)
        throw std::exception("Invalid return type for given call");

    for (int i = 1; i < sizeof...(Args) + 1; i++)
    {
        if (type_check[i] != argument_types[i])
            throw std::exception("Invalid argument type for the given call");
    }

    return Return(*func)(Args...)(args...);
}
};

1 个答案:

答案 0 :(得分:1)

TypeToEnum<std::forward<Args>>::valueTypeToEnum<Args>::value...,但我会改为

template<typename Return,typename... Args>
Return invoke(Args...&& args){
  static const int type_check[] = {
    TypeToEnum<Return>::value,TypeToEnum<typename std::decay<Args>::type>::value...
  };

  if (type_check[0] != return_type)
    throw std::exception("Invalid return type for given call");

  for (int i = 1; i <= sizeof...(Args); i++)
  {
    if (type_check[i] != argument_types[i])
      throw std::exception("Invalid argument type for the given call");
  }

  typedef Return(*func_t)(typename std::decay<Args>::type...);
  return static_cast<func_t>(function)( std::forward<Args>(args) );
}

作为第一关。然后我将decay替换为正确处理std::reference_wrapper的自定义类型映射,因此调用者可以说&#34;我希望这个参数是ref&#34;说invoke( std::ref(x) )

接下来,我会考虑使用typeid而不是所有机器。除了其他问题之外,你的哈希值并不完全可靠。