How did you guys learn multithreading?


#1

I’m looking at adding some threads to speed up the performance of my game and offload some of the processing on the main thread, what is the best way to learn multithreading in Haxe? Are there any tutorials you would suggest?


#2

I looked at this haxe doc.
http://old.haxe.org/doc/neko/threads
It only covers Neko but it’s practically the same for cpp(c++)


#3

A principle in multi-threading is that reading a value from multiple threads is generally safe, but writing from multiple threads is a no-no. That is where objects (such as a Mutex) come in.

For simple access to threads, I would recommend you consider looking at lime.system.BackgroundWorker and lime.system.ThreadPool, or even lime.app.Future, which all support threads.

Future (with async = true)

var future = new Future (function () {
    return 1000;
}, true);
future.onComplete (function (value:Int) {
    trace ("Result: " + value);
});

BackgroundWorker

var worker = new BackgroundWorker ();
worker.doWork.add (function (message) {
    for (i in 0...1000) {
        message++;
        worker.sendProgress (i / 1000);
    }
    worker.sendComplete (message);
});
worker.onProgress.add (function (message) {
    trace ("Progress: " + message + "%");
});
worker.onComplete.add (function (message) {
    trace ("Result: " + message);
});
worker.run (100);

(messages are optional, and dynamic, so it can be a generic object, or a single value)

ThreadPool

var threadPool = new ThreadPool (1, 4);
threadPool.doWork.add (function (message) {
    var result = message.value;
    for (i in 0...1000) {
        result++;
        threadPool.sendProgress ({ id: message.id, progress: i / 1000 });
    }
    threadPool.sendComplete ({ id: message.id, result: result });
});
threadPool.onProgress.add (function (message) {
    trace ("Progress: " + message.progress + "% (id: " + message.id + ")");
});
threadPool.onComplete.add (function (message) {
    trace ("Result: " + message.result + " (id: " + message.id + ")");
});
threadPool.queue ({ id: 1, value: 100 });

(The ‘message’ value works the same as in BackgroundWorker, but usually you would want to send some identifying information, so that when you receive a progress or complete or error event from your worker thread, you know which job it is, since a ThreadPool can do multiple jobs at once, depending on the number of threads you give it.)

You should be careful that the work you do in a thread is thread-safe. For example, calling something that relates to OpenFL’s rendering won’t be thread safe