Concurrency
Synchronization: with_mutex/2, mutex_create/1, thread_local predicates, message_queue_create/1, thread_signal/2, thread_pool_create/3.
39.1 Threads (SWI-Prolog)
Synchronization: with_mutex/2, mutex_create/1, thread_local predicates, message_queue_create/1, thread_signal/2, thread_pool_create/3.
?- thread_create(worker(1), Id, []), thread_join(Id, Status).
worker(N) :- thread_self(Me), format("worker ~w in thread ~w~n", [N, Me]).
% Message queues
?- thread_self(Me),
thread_create((thread_get_message(ping(From)), thread_send_message(From, pong)), T, []),
thread_send_message(T, ping(Me)),
thread_get_message(pong).
% Parallel map
?- concurrent_maplist([X, Y]>>(Y is X * X), [1, 2, 3, 4], L).
?- concurrent(4, [G1, G2, G3], []). % run goals with 4 workers
?- first_solution(X, [solve_a(X), solve_b(X)], []). % race strategies
?- concurrent_forall(member(X, Items), process(X)).39.2 Engines (SWI)
Engines are coroutines that run a goal and yield answers on demand:
Use for generators, agents, lazy evaluation, and stateful aggregation.
?- engine_create(X, member(X, [a, b, c]), E),
engine_next(E, A1), engine_next(E, A2). % A1 = a, A2 = b
?- engine_create(S, sum_loop(0, S), E), engine_post(E, 5, R). % send data in39.3 Global variables
b_setval(counter, 0), b_getval(counter, V). % backtrackable
nb_setval(total, 0), nb_getval(total, V). % non-backtrackable39.4 Delimited continuations
Basis for effect-handler-style programming (iterators, DCG-like state threading, tabling implementation in SWI).
reset(Goal, Ball, Cont) % run Goal until it calls shift(Ball)
shift(Ball)