| /* Some performance benchmarks of boost.signals vs signals2 */ |
| |
| // Copyright Frank Mori Hess 2008. |
| // Distributed under the Boost Software License, Version |
| // 1.0. (See accompanying file LICENSE_1_0.txt or copy at |
| // http://www.boost.org/LICENSE_1_0.txt) |
| |
| #include <cstdlib> |
| #include <iostream> |
| #include <boost/bind.hpp> |
| #include <boost/progress.hpp> |
| #include <boost/signals2.hpp> |
| #include <boost/signals.hpp> |
| |
| typedef boost::signals2::signal<void (int), |
| boost::signals2::optional_last_value<void>, |
| int, |
| std::less<int>, |
| boost::function<void (int)>, |
| boost::function<void (const boost::signals2::connection &, int)>, |
| boost::signals2::dummy_mutex> |
| new_signal_type; |
| typedef boost::signal<void (int)> old_signal_type; |
| |
| class myslot |
| { |
| public: |
| void operator()(int) {}; |
| }; |
| |
| class trackable_slot: public myslot, public boost::signals::trackable |
| {}; |
| |
| template<typename Signal> |
| void benchmark_invocation(unsigned num_connections) |
| { |
| static const unsigned num_invocations = 1000000; |
| |
| Signal signal; |
| std::cout << num_connections << " connections, invoking " << num_invocations << " times: "; |
| unsigned n; |
| for(n = 0; n < num_connections; ++n) |
| { |
| signal.connect(myslot()); |
| } |
| { |
| boost::progress_timer timer; |
| unsigned i; |
| for(i = 0; i < num_invocations; ++i) |
| { |
| signal(0); |
| } |
| } |
| } |
| |
| void benchmark_old_tracked_invocation(unsigned num_connections) |
| { |
| static const unsigned num_invocations = 1000000; |
| |
| old_signal_type signal; |
| std::cout << "boost::signal, " << num_connections << " connections, tracking enabled, invoking " << num_invocations << " times: "; |
| unsigned n; |
| trackable_slot tslot; |
| for(n = 0; n < num_connections; ++n) |
| { |
| signal.connect(tslot); |
| } |
| { |
| boost::progress_timer timer; |
| unsigned i; |
| for(i = 0; i < num_invocations; ++i) |
| { |
| signal(0); |
| } |
| } |
| } |
| |
| void benchmark_new_tracked_invocation(unsigned num_connections) |
| { |
| static const unsigned num_invocations = 1000000; |
| |
| new_signal_type signal; |
| std::cout << "boost::signals2::signal, " << num_connections << " connections, tracking enabled, invoking " << num_invocations << " times: "; |
| boost::shared_ptr<int> trackable_ptr(new int(0)); |
| unsigned n; |
| for(n = 0; n < num_connections; ++n) |
| { |
| new_signal_type::slot_type slot((myslot())); |
| slot.track(trackable_ptr); |
| signal.connect(slot); |
| } |
| { |
| boost::progress_timer timer; |
| unsigned i; |
| for(i = 0; i < num_invocations; ++i) |
| { |
| signal(0); |
| } |
| } |
| } |
| |
| template<typename Signal> class connection_type; |
| template<> class connection_type<old_signal_type> |
| { |
| public: |
| typedef boost::signals::connection type; |
| }; |
| template<> class connection_type<new_signal_type> |
| { |
| public: |
| typedef boost::signals2::connection type; |
| }; |
| |
| template<typename Signal> |
| void benchmark_connect_disconnect() |
| { |
| static const unsigned num_connections = 1000000; |
| std::vector<typename connection_type<Signal>::type> connections(num_connections); |
| |
| Signal signal; |
| std::cout << "connecting " << num_connections << " connections then disconnecting: "; |
| unsigned n; |
| { |
| boost::progress_timer timer; |
| for(n = 0; n < num_connections; ++n) |
| { |
| connections.at(n) = signal.connect(myslot()); |
| } |
| for(n = 0; n < num_connections; ++n) |
| { |
| connections.at(n).disconnect(); |
| } |
| } |
| } |
| |
| int main(int argc, const char **argv) |
| { |
| std::cout << "\n"; |
| { |
| std::cout << "boost::signals2::signal, "; |
| benchmark_invocation<new_signal_type>(1); |
| } |
| { |
| std::cout << "boost::signal, "; |
| benchmark_invocation<old_signal_type>(1); |
| } |
| |
| std::cout << "\n"; |
| { |
| std::cout << "boost::signals2::signal, "; |
| benchmark_invocation<new_signal_type>(10); |
| } |
| { |
| std::cout << "boost::signal, "; |
| benchmark_invocation<old_signal_type>(10); |
| } |
| |
| std::cout << "\n"; |
| benchmark_new_tracked_invocation(1); |
| benchmark_old_tracked_invocation(1); |
| |
| std::cout << "\n"; |
| benchmark_new_tracked_invocation(10); |
| benchmark_old_tracked_invocation(10); |
| |
| std::cout << "\n"; |
| { |
| std::cout << "boost::signals2::signal, "; |
| benchmark_connect_disconnect<new_signal_type>(); |
| } |
| { |
| std::cout << "boost::signal, "; |
| benchmark_connect_disconnect<old_signal_type>(); |
| } |
| } |