Add support for seeing if a dispatch exists
This commit is contained in:
parent
b806ff20cc
commit
ee9c71de4c
@ -449,6 +449,18 @@ namespace dispatchkit
|
|||||||
std::vector<Boxed_Value>(params.begin() + 1, params.end()))));
|
std::vector<Boxed_Value>(params.begin() + 1, params.end()))));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Boxed_Value call_exists(const std::vector<Boxed_Value> ¶ms)
|
||||||
|
{
|
||||||
|
if (params.size() < 1)
|
||||||
|
{
|
||||||
|
throw arity_error(params.size(), 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
boost::shared_ptr<Proxy_Function> f = boxed_cast<boost::shared_ptr<Proxy_Function> >(params[0]);
|
||||||
|
|
||||||
|
return Boxed_Value(f->types_match(std::vector<Boxed_Value>(params.begin() + 1, params.end())));
|
||||||
|
}
|
||||||
|
|
||||||
static void bootstrap(Dispatch_Engine &s)
|
static void bootstrap(Dispatch_Engine &s)
|
||||||
{
|
{
|
||||||
s.register_type<void>("void");
|
s.register_type<void>("void");
|
||||||
@ -488,6 +500,9 @@ namespace dispatchkit
|
|||||||
s.register_function(boost::shared_ptr<Proxy_Function>(new Dynamic_Proxy_Function(boost::bind(&bind_function, _1))),
|
s.register_function(boost::shared_ptr<Proxy_Function>(new Dynamic_Proxy_Function(boost::bind(&bind_function, _1))),
|
||||||
"bind");
|
"bind");
|
||||||
|
|
||||||
|
s.register_function(boost::shared_ptr<Proxy_Function>(new Dynamic_Proxy_Function(boost::bind(&call_exists, _1))),
|
||||||
|
"call_exists");
|
||||||
|
|
||||||
register_function(s, &type_match, "type_match");
|
register_function(s, &type_match, "type_match");
|
||||||
register_function(s, &bool_and<bool, bool>, "&&");
|
register_function(s, &bool_and<bool, bool>, "&&");
|
||||||
register_function(s, &bool_or<bool, bool>, "||");
|
register_function(s, &bool_or<bool, bool>, "||");
|
||||||
|
@ -26,7 +26,7 @@ namespace dispatchkit
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool operator==(const Proxy_Function &f) const
|
virtual bool operator==(const Proxy_Function &f) const
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -38,11 +38,31 @@ namespace dispatchkit
|
|||||||
return dispatch(m_funcs, params);
|
return dispatch(m_funcs, params);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual std::vector<Type_Info> get_param_types()
|
virtual std::vector<Type_Info> get_param_types() const
|
||||||
{
|
{
|
||||||
return std::vector<Type_Info>();
|
return std::vector<Type_Info>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual bool types_match(const std::vector<Boxed_Value> &types) const
|
||||||
|
{
|
||||||
|
typedef std::vector<std::pair<std::string, boost::shared_ptr<Proxy_Function> > > function_vec;
|
||||||
|
|
||||||
|
function_vec::const_iterator begin = m_funcs.begin();
|
||||||
|
function_vec::const_iterator end = m_funcs.end();
|
||||||
|
|
||||||
|
while (begin != end)
|
||||||
|
{
|
||||||
|
if (begin->second->types_match(types))
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
++begin;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<std::pair<std::string, boost::shared_ptr<Proxy_Function> > > m_funcs;
|
std::vector<std::pair<std::string, boost::shared_ptr<Proxy_Function> > > m_funcs;
|
||||||
};
|
};
|
||||||
|
@ -2,6 +2,8 @@
|
|||||||
|
|
||||||
#define gettypeinfo(z,n,text) ti.push_back(Get_Type_Info<Param ## n>::get());
|
#define gettypeinfo(z,n,text) ti.push_back(Get_Type_Info<Param ## n>::get());
|
||||||
#define casthelper(z,n,text) ,dispatchkit::boxed_cast< Param ## n >(params[n])
|
#define casthelper(z,n,text) ,dispatchkit::boxed_cast< Param ## n >(params[n])
|
||||||
|
#define comparetype(z,n,text) && ((Get_Type_Info<Param ## n>::get() == params[n].get_type_info()))
|
||||||
|
#define trycast(z,n,text) dispatchkit::boxed_cast<Param ## n>(params[n]);
|
||||||
|
|
||||||
|
|
||||||
#ifndef BOOST_PP_IS_ITERATING
|
#ifndef BOOST_PP_IS_ITERATING
|
||||||
@ -119,8 +121,9 @@ namespace dispatchkit
|
|||||||
public:
|
public:
|
||||||
virtual ~Proxy_Function() {}
|
virtual ~Proxy_Function() {}
|
||||||
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms) = 0;
|
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms) = 0;
|
||||||
virtual std::vector<Type_Info> get_param_types() = 0;
|
virtual std::vector<Type_Info> get_param_types() const = 0;
|
||||||
virtual bool operator==(const Proxy_Function &) const = 0;
|
virtual bool operator==(const Proxy_Function &) const = 0;
|
||||||
|
virtual bool types_match(const std::vector<Boxed_Value> &types) const = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
class Dynamic_Proxy_Function : public Proxy_Function
|
class Dynamic_Proxy_Function : public Proxy_Function
|
||||||
@ -131,11 +134,16 @@ namespace dispatchkit
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool operator==(const Proxy_Function &f) const
|
virtual bool operator==(const Proxy_Function &f) const
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual bool types_match(const std::vector<Boxed_Value> &types) const
|
||||||
|
{
|
||||||
|
return (m_arity < 0 || types.size() == size_t(m_arity));
|
||||||
|
}
|
||||||
|
|
||||||
virtual ~Dynamic_Proxy_Function() {}
|
virtual ~Dynamic_Proxy_Function() {}
|
||||||
|
|
||||||
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms)
|
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms)
|
||||||
@ -148,7 +156,7 @@ namespace dispatchkit
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual std::vector<Type_Info> get_param_types()
|
virtual std::vector<Type_Info> get_param_types() const
|
||||||
{
|
{
|
||||||
return build_param_type_list(m_f);
|
return build_param_type_list(m_f);
|
||||||
}
|
}
|
||||||
@ -167,14 +175,25 @@ namespace dispatchkit
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool operator==(const Proxy_Function &f) const
|
virtual bool operator==(const Proxy_Function &f) const
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~Bound_Function() {}
|
virtual ~Bound_Function() {}
|
||||||
|
|
||||||
|
virtual bool types_match(const std::vector<Boxed_Value> &types) const
|
||||||
|
{
|
||||||
|
std::vector<Boxed_Value> params = build_param_list(types);
|
||||||
|
return m_f->types_match(params);
|
||||||
|
}
|
||||||
|
|
||||||
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms)
|
virtual Boxed_Value operator()(const std::vector<Boxed_Value> ¶ms)
|
||||||
|
{
|
||||||
|
return (*m_f)(build_param_list(params));
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<Boxed_Value> build_param_list(const std::vector<Boxed_Value> ¶ms) const
|
||||||
{
|
{
|
||||||
typedef std::vector<Boxed_Value>::const_iterator pitr;
|
typedef std::vector<Boxed_Value>::const_iterator pitr;
|
||||||
|
|
||||||
@ -208,10 +227,10 @@ namespace dispatchkit
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (*m_f)(args);
|
return args;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual std::vector<Type_Info> get_param_types()
|
virtual std::vector<Type_Info> get_param_types() const
|
||||||
{
|
{
|
||||||
return std::vector<Type_Info>();
|
return std::vector<Type_Info>();
|
||||||
}
|
}
|
||||||
@ -247,11 +266,16 @@ namespace dispatchkit
|
|||||||
return call_func(m_f, params);
|
return call_func(m_f, params);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual std::vector<Type_Info> get_param_types()
|
virtual std::vector<Type_Info> get_param_types() const
|
||||||
{
|
{
|
||||||
return build_param_type_list(m_f);
|
return build_param_type_list(m_f);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual bool types_match(const std::vector<Boxed_Value> &types) const
|
||||||
|
{
|
||||||
|
return compare_types(m_f, types);
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Func m_f;
|
Func m_f;
|
||||||
};
|
};
|
||||||
@ -315,6 +339,28 @@ namespace dispatchkit
|
|||||||
return Handle_Return<Ret>()(boost::bind(f BOOST_PP_REPEAT(n, casthelper, ~)));
|
return Handle_Return<Ret>()(boost::bind(f BOOST_PP_REPEAT(n, casthelper, ~)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename Ret BOOST_PP_COMMA_IF(n) BOOST_PP_ENUM_PARAMS(n, typename Param)>
|
||||||
|
bool compare_types(const boost::function<Ret (BOOST_PP_ENUM_PARAMS(n, Param))> &,
|
||||||
|
const std::vector<Boxed_Value> ¶ms)
|
||||||
|
{
|
||||||
|
if (params.size() != n)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
bool val = true BOOST_PP_REPEAT(n, comparetype, ~);
|
||||||
|
if (val) return true;
|
||||||
|
|
||||||
|
try {
|
||||||
|
BOOST_PP_REPEAT(n, trycast, ~);
|
||||||
|
} catch (const bad_boxed_cast &) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
x
Reference in New Issue
Block a user