Boost logo

Boost :

Subject: [boost] [type_erasure] Downcasting is now possible
From: Steven Watanabe (watanabesj_at_[hidden])
Date: 2015-03-07 23:27:23


AMDG

  I've been asked about a function for downcasting
an any several times, and I finally implemented it.
Short story: you can now use dynamic_any_cast to
convert between two arbitrary any types.

  Here's a quick example which tries to cast a
boost::any equivalent to a boost::function
equivalent.

using plain_any = any<mpl::vector<
    copy_constructible<>,
    relaxed> >;

template<class Sig>
using any_function = any<mpl::vector<
    callable<Sig>,
    copy_constructible<>,
    relaxed> >;

bool try_call(const plain_any& arg) {
  try {
    auto fun = dynamic_any_cast<any_function<void()> >(arg);
    fun();
  } catch(bad_any_cast&) {
    return false;
  }
  return true;
}

void global_register() {
  register_binding<copy_constructible<>, void(*)()>();
  register_binding<typeid_<>, void(*)()>();
  register_binding<callable<void()>, void(*)()>();
}

void do_something() {
    std::cout << 42 << std::endl;
}

int main() {
    global_register();
    plain_any x = &do_something;
    if(try_call(x)) {
        std::cout << "x is a function" << std::endl;
    }
    plain_any y = 10;
    if(!try_call(y)) {
        std::cout << "y is NOT a function" << std::endl;
    }
}

  The calls to register_binding are necessary for
this to work, unfortunately. I don't think it's
possible to implement dynamic_any_cast without
some kind of registration, but at least it only
needs to be called once for each concept/type
combination. If anyone has any better ideas
about how to handle this, I'd love to hear it.

Comments, questions, and criticism are welcome.

In Christ,
Steven Watanabe


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk