WorkerThreadPool

Inherits:Object

A singleton that allocates someThreads on startup, used to offload tasks to these threads.

Description

TheWorkerThreadPool singleton allocates a set ofThreads (called worker threads) on project startup and provides methods for offloading tasks to them. This can be used for simple multithreading without having to createThreads.

Tasks hold theCallable to be run by the threads.WorkerThreadPool can be used to create regular tasks, which will be taken by one worker thread, or group tasks, which can be distributed between multiple worker threads. Group tasks execute theCallable multiple times, which makes them useful for iterating over a lot of elements, such as the enemies in an arena.

Here's a sample on how to offload an expensive function to worker threads:

varenemies=[]# An array to be filled with enemies.funcprocess_enemy_ai(enemy_index):varprocessed_enemy=enemies[enemy_index]# Expensive logic...func_process(delta):vartask_id=WorkerThreadPool.add_group_task(process_enemy_ai,enemies.size())# Other code...WorkerThreadPool.wait_for_group_task_completion(task_id)# Other code that depends on the enemy AI already being processed.

The above code relies on the number of elements in theenemies array remaining constant during the multithreaded part.

Note: Using this singleton could affect performance negatively if the task being distributed between threads is not computationally expensive.

Tutorials

Methods

int

add_group_task(action:Callable, elements:int, tasks_needed:int = -1, high_priority:bool = false, description:String = "")

int

add_task(action:Callable, high_priority:bool = false, description:String = "")

int

get_group_processed_element_count(group_id:int)const

bool

is_group_task_completed(group_id:int)const

bool

is_task_completed(task_id:int)const

void

wait_for_group_task_completion(group_id:int)

Error

wait_for_task_completion(task_id:int)


Method Descriptions

intadd_group_task(action:Callable, elements:int, tasks_needed:int = -1, high_priority:bool = false, description:String = "")🔗

Addsaction as a group task to be executed by the worker threads. TheCallable will be called a number of times based onelements, with the first thread calling it with the value0 as a parameter, and each consecutive execution incrementing this value by 1 until it reacheselement-1.

The number of threads the task is distributed to is defined bytasks_needed, where the default value-1 means it is distributed to all worker threads.high_priority determines if the task has a high priority or a low priority (default). You can optionally provide adescription to help with debugging.

Returns a group task ID that can be used by other methods.

Warning: Every task must be waited for completion usingwait_for_task_completion() orwait_for_group_task_completion() at some point so that any allocated resources inside the task can be cleaned up.


intadd_task(action:Callable, high_priority:bool = false, description:String = "")🔗

Addsaction as a task to be executed by a worker thread.high_priority determines if the task has a high priority or a low priority (default). You can optionally provide adescription to help with debugging.

Returns a task ID that can be used by other methods.

Warning: Every task must be waited for completion usingwait_for_task_completion() orwait_for_group_task_completion() at some point so that any allocated resources inside the task can be cleaned up.


intget_group_processed_element_count(group_id:int)const🔗

Returns how many times theCallable of the group task with the given ID has already been executed by the worker threads.

Note: If a thread has started executing theCallable but is yet to finish, it won't be counted.


boolis_group_task_completed(group_id:int)const🔗

Returnstrue if the group task with the given ID is completed.

Note: You should only call this method between adding the group task and awaiting its completion.


boolis_task_completed(task_id:int)const🔗

Returnstrue if the task with the given ID is completed.

Note: You should only call this method between adding the task and awaiting its completion.


voidwait_for_group_task_completion(group_id:int)🔗

Pauses the thread that calls this method until the group task with the given ID is completed.


Errorwait_for_task_completion(task_id:int)🔗

Pauses the thread that calls this method until the task with the given ID is completed.

Returns@GlobalScope.OK if the task could be successfully awaited.

Returns@GlobalScope.ERR_INVALID_PARAMETER if a task with the passed ID does not exist (maybe because it was already awaited and disposed of).

Returns@GlobalScope.ERR_BUSY if the call is made from another running task and, due to task scheduling, there's potential for deadlocking (e.g., the task to await may be at a lower level in the call stack and therefore can't progress). This is an advanced situation that should only matter when some tasks depend on others (in the current implementation, the tricky case is a task trying to wait on an older one).


User-contributed notes

Please read theUser-contributed notes policy before submitting a comment.