How can I wait for all the threads in a ThreadPool to complete?

I want to use a thread pool to do work concurrently.
I’ve copied and adapted the threadpool.vala eg and it works.
However, I can’t see how to wait for the thread pool to finish. There’s no ThreadPool.join(). Here’s the code with a comment:

class Worker {
    public string thread_name { private set; get; }
    public int x_times { private set; get; }
    public int total { private set; get; }

    public Worker (string name, int x) {
        this.thread_name = name;
        this.x_times = x;
	this.total = 0;
    }

    public void run() {
        for (int i = 0; i < this.x_times; i++) {
            print ("%s: %d/%d\n", this.thread_name, i + 1, this.x_times);
	    this.total++;
            Thread.usleep(500000);
        }
    }
}

void main() {
    Worker[] workers = {
        new Worker("Thread A", 5),
        new Worker("Thread B", 7),
        new Worker("Thread C", 3),
    };
    try {
        ThreadPool<Worker> pool = new ThreadPool<Worker>.with_owned_data ((worker) => {
            worker.run();
        }, 2, false);

	foreach (Worker worker in workers) {
	    pool.add(worker);
	}

        uint waiting = pool.unprocessed();
        uint allowed = pool.get_max_threads();
        uint running = pool.get_num_threads();
        print ("%u/%u threads are running, %u outstanding.\n", running, allowed, waiting);
    } catch (ThreadError e) {
        print ("ThreadError: %s\n", e.message);
    }
    /////// How do I wait for threads to complete? ////////////////
    print("End of Threads");
    foreach (Worker worker in workers) {
	print("%s: %d\n", worker.thread_name, worker.total);
    }
}

And here’s a typical run:

2/2 threads are running, 3 outstanding.
Thread A: 1/5
Thread B: 1/7
Thread B: 2/7
Thread A: 2/5
Thread B: 3/7
Thread A: 3/5
Thread B: 4/7
Thread A: 4/5
Thread B: 5/7
Thread A: 5/5
Thread B: 6/7
Thread C: 1/3
Thread C: 2/3
Thread B: 7/7
Thread C: 3/3
End of ThreadsThread A: 5
Thread B: 7
Thread C: 3

I want the message “End of Threads” to really come at the end: at that point I want to sum the totals.

1 Like

GThreadPool does not support that, it would have to be built separately. You can use GAsyncQueue to have a thread-safe work queue that can wait on the results from another thread.

Technically it can be done more efficiently with just an atomic counter and a futex, if there is a good way to use that from Vala.

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.