# Thread creation in first\_solution

**URL:** <https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686>\
**Category:** General\
**Created:** [December 21, 2024, 12:15am UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686 "2024-12-21T00:15:56Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![maximilianocristia](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/maximilianocristia/32/5377_2.png) [@maximilianocristia](https://swi-prolog.discourse.group/u/maximilianocristia)\
**Post date:** [December 21, 2024, 12:15am UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686/1 "2024-12-21T00:15:56Z")

</div>

Hello,

What’s the strategy of thread creation in first\_solution/3? Is it like in concurrent\_maplist (i.e. the number of threads is the minimum of the list length and the number of cores available)? If the length of :Goals is larger than the number of cores available, once one of the goals fails a new element of :Goals is launched in that now unused core?

Hope the questions are clear.

Thanks!

Maxi

---

<div class="post-metadata">

**Author:** ![jan](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/jan/32/4_2.png) [@jan](https://swi-prolog.discourse.group/u/jan)\
**Post date:** [December 21, 2024, 11:03am UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686/2 "2024-12-21T11:03:44Z")

</div>

Click the `(:-)` link to the source ([thread.pl](https://www.swi-prolog.org/pldoc/doc/_SWI_/library/thread.pl?show=src#first_solution/3)) and find

```prolog
create_solvers([], _, _, _, [], _).
create_solvers([H|T], M, X, Done, [Id|IDs], Options) :-
    thread_create(solve(M:H, X, Done), Id, Options),
    create_solvers(T, M, X, Done, IDs, Options).

```

For short, it creates a thread per solver, regardless of the number of cores. Where concurrent\_maplist/3 creates as many threads as cores (or less if the list is shorter).

first\_solution/3 is primarily intended to solve problems for which you have alternative algorithms to solve them but there is no good way to predict which one is better. So, you want to try them concurrently, even if you have fewer cores than algorithms.

---

<div class="post-metadata">

**Author:** ![maximilianocristia](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/maximilianocristia/32/5377_2.png) [@maximilianocristia](https://swi-prolog.discourse.group/u/maximilianocristia)\
**Post date:** [December 22, 2024, 4:57pm UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686/3 "2024-12-22T16:57:01Z")

</div>

Thanks Jan!

Sorry for this but I’m not sure what I’m doing wrong here.

```prolog
?- first_solution([X],[(X=a,1=2),(X=a,1=2),(X=b)],[]).
false.

?- first_solution([X],[(X=a,1=2),(X=a,1=2),(X=b)],[]).
X = b.

```

I’ve run the same query over and over again sometimes getting false and others X = b.

If `(X=a,1=2)` is repeated several times (32 in my case) leaving `X=b` as the last element of the list the answer is always false (or at least after executing the query over 10 times false is the only answer I get).

Thanks again!

---

<div class="post-metadata">

**Author:** ![Boris](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/boris/32/7486_2.png) [@Boris](https://swi-prolog.discourse.group/u/Boris)\
**Post date:** [December 22, 2024, 6:02pm UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686/4 "2024-12-22T18:02:06Z")

</div>

What exactly do you expect to happen? The docs say,

> Try alternative solvers concurrently, returning the first answer. In a typical scenario, solving any of the goals in Goals is satisfactory for the application to continue. As soon as one of the tried alternatives is successful, all the others are killed and [first\_solution/3](https://www.swi-prolog.org/pldoc/man?predicate=first_solution/3) succeeds.

In the case of `(X=a, 1=2)`: this is always false (right??) so as soon as it fails you get your `false`. This sounds correct to me?

So, what were you expecting to happen here?

Are you sure you didn’t mean:

```prolog
first_solution([X],[(X=a,1=2),(X=a,1=2),(X=b)],[on_fail(continue)]).

```

This is what the docs say:

> If `stop` (default), terminate all threads and stop with the failure. If `continue`, keep waiting.

---

<div class="post-metadata">

**Author:** ![maximilianocristia](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/maximilianocristia/32/5377_2.png) [@maximilianocristia](https://swi-prolog.discourse.group/u/maximilianocristia)\
**Post date:** [December 22, 2024, 6:30pm UTC](https://swi-prolog.discourse.group/t/thread-creation-in-first-solution/8686/5 "2024-12-22T18:30:26Z")

</div>

Ahhh, OK, now I see. I was thinking in getting a positive answer so I thought that if a thread returned false first\_solution will wait until another thread returned something different from false.

Thanks for the clarification!

Maxi
