Wednesday, August 24, 2011

libcppa vs. Erlang vs. Scala Performance

I recently found a Scala Actor vs. Erlang Performance test on github.

The test benchmarks the speed of message handling and I decided to port it to libcppa. This is the full source code for a sequential-send-version (sending 3,000,000 messages):

#include <iostream>
#include "cppa/cppa.hpp"
#include <boost/progress.hpp>

using std::cout;
using std::endl;
using boost::timer;
using namespace cppa;

void counter_actor()
{
    long count = 0;
    receive_loop
    (   
        on<atom("Get")>() >> [&]()
        {   
            reply(count);
            count = 0;
        },  
        on<atom("AddCount"), long>() >> [&](long val)
        {   
            count += val;
        }   
    );  
}

long the_test(int msg_count)
{
    constexpr long val = 100;
    auto counter = spawn(counter_actor);
    for (int i = 0; i < msg_count; ++i)
    {   
        send(counter, atom("AddCount"), val);
    }   
    send(counter, atom("Get"));
    long result = 0;
    receive
    (   
        on<long>() >> [&](long value)
        {   
            result = value;
        }   
    );  
    send(counter, atom(":Exit"), exit_reason::user_defined);
    return result;
}

void run_test(int msg_count)
{
    timer t0; 
    long count = the_test(msg_count);
    auto elapsed = t0.elapsed();
    cout << "Count is " << count << endl
         << "Test took " << elapsed << " seconds" << endl
         << "Throughput = " << (msg_count / elapsed)
                            << " per sec" << endl;
}

int main()
{
    run_test(3000000);
    await_all_others_done();
    return 0;
}


Results (average value of 5 runs)


LanguageTime(s)Throughput (msg/s)
Erlang OTP~9~333,333.333
Erlang "bare receive"~7~428,571.429
Scala 2.9~9~333,333.333
libcppa~12~250,000


System: 2.66 GHz Intel Core i7 (dual core); Mac OS 10.7.1

The source code can be found in the folder gen_server on github.


Note: This benchmark results are outdated. The current version of libcppa runs the gen_server benchmark in ~5.5 seconds.

Please see the mixed scenario post for a more detailed benchmark.