提升绑定可变参数重载决议

时间:2015-02-02 09:02:15

标签: c++ templates bind variadic-templates

 #include <cstdio>
 #include <string>
 #include <boost/bind.hpp>
 #include <boost/function.hpp>
 #include <boost/lexical_cast.hpp>

 struct CLASS{

   template<typename T, typename ... Args>
   void enqueue(T const & t, Args const & ... args){
      this->concatenate(t,args ...);
   }

   template<typename T, typename ... Args>
   void concatenate(T t, Args ... args){
      boost::function<void()> f 
            = boost::bind(&CLASS::push_,this,
                          boost::bind(&CLASS::stringer<T const &,
                                      Args const & ...>,
                                      this,boost::ref(t),boost::ref(args)...));
   }

   template<typename T, typename ... Args>
   std::string stringer(T const & t, Args const & ... args){
      return stringer(t) + stringer(args...);
   }


   template <typename T>
   std::string stringer(T const & t){
      return boost::lexical_cast<std::string>(t);
   }

   void push_(std::string const & s){
      std::fprintf(stderr,"%s\n",s.c_str());
   }

};



 int main(){

    CLASS c;

    c.enqueue(42,"hello",35);

    // below commented enqueue fails to compile
    //c.enqueue("abc", 100," for ", 42000,"sadada ", 4.3, "zzzzz\n",42,42);                                   

    return 0;
 }

在上面的main函数中,注释行无法编译,尽管未注释的enqueue确实有效。我有一种感觉问题是由stringer函数展开variadics并且boost :: bind无法找出重载或其他东西。 如何解决此问题,以便enqueue适用于任何输入组合?

1 个答案:

答案 0 :(得分:0)

在c ++ 11下,我们无法绑定重载函数。 但是在C ++ 14下有解决方案: 例如:

struct ulong_ip_tag{};
struct string_ip_tag{};
struct resolved_ip_tag{};
struct invalid_ip_tag{};

template<typename _Type, typename _Handler>
void handler(_Handler, _Type)
{
    std::cout << "other type" << std::endl;
}

template<typename _Handler>
void handler(_Handler, resolved_ip_tag)
{
    std::cout << typeid(resolved_ip_tag).name() << std::endl;
}

template<typename _Handler>
void handler(_Handler, string_ip_tag)
{
    std::cout << typeid(string_ip_tag).name() << std::endl;
}

template<typename _Handler>
void handler(_Handler, ulong_ip_tag)
{
    std::cout << typeid(ulong_ip_tag).name() << std::endl;
}

void test(){}

int main()
{
     //auto--- under c++14
     auto b = [](auto arg1,auto arg2){handler(arg1,arg2)};
     std::bind(b,test,ulong_ip_tag());
}