Répondre

3

Oui, vous pouvez le faire assez bien avec le message passant en Concurrent ML. Ne soyez pas rebutés par l'âge du système; Les documents book de John Reppy et les documents sont d'excellents guides sur le sujet. Belles choses!

1

Toutes les mises en œuvre que j'ai vu des producteurs-consommateurs en SML ont été contraints de compter sur ref s (afin de maintenir une file d'attente d'éléments « dormants »), donc Je serais enclin à dire "non".

3

Avoir plusieurs threads nécessite nécessairement des actions impures (non-fonctionnelles). La programmation fonctionnelle pure considère que votre application est l'évaluation d'une fonction. Le concept d'évaluer simultanément deux choses et de passer des données entre eux n'est pas significatif dans ce cadre.

Bien que l'on puisse évaluer plusieurs parties d'une fonction en parallèle, comme dans l'opérateur ``par de Haskell, ce n'est pas la même chose que le problème producteur-consommateur, et je ne pense pas que vous puissiez le résoudre d'une manière fonctionnelle.

+1

Je n'ai pas vu la notion de plusieurs threads dans la question. Notez qu'une * implémentation * d'une abstraction purement fonctionnelle peut utiliser la concurrence. La concurrence elle-même n'a pas besoin d'afficher le modèle sémantique/utilisateur. De plus, la programmation fonctionnelle * paresseuse ressemble beaucoup à la concurrence. Beaucoup de calculs suspendus (thunks) attendent la demande (réduction à la forme normale de la tête faible) d'autres calculs, à quel point ils deviennent temporairement actifs. Malgré toute cette implémentation de "concurrence" (style coroutine), la sémantique est pure et simple, permettant ainsi un raisonnement correct et malléable. – Conal

1

Il existe plusieurs façons de résoudre ce problème; chacun a des inconvénients différents. Par exemple, le "put" pourrait générer un nouveau thread à chaque fois. De cette façon, vous n'auriez pas besoin d'un tampon du tout. Si beaucoup de demandes arrivent, vous générez beaucoup de threads jusqu'à ce que votre CPU soit plus occupé à passer d'un thread à l'autre qu'en les exécutant. Mais cela ne fait que déplacer le problème de votre code dans le système d'exploitation: à un certain point, vous devez toujours synchroniser l'accès à une variable en mémoire. Le système d'exploitation doit maintenir une liste de threads et l'accès à cette liste doit être synchronisé. Soit vous voulez limiter le nombre de threads (alors un "put" doit être capable de lire la variable alors que les threads peuvent se terminer en même temps et décrémenter -> à nouveau l'accès synchronisé). Ou vous risquez de manquer de ressources car vous avez trop de threads.

Vous pourriez poster un message quand "put" est appelé et les consommateurs pourraient écouter le message. Mais ce n'est qu'une manière complexe d'implémenter "attendre" les threads. Et vous avez besoin d'un moyen de vous assurer que seul un consommateur unique reçoit le message. Encore une fois, vous aurez besoin d'une structure de données synchronisée. Donc, à la fin, ce n'est pas vraiment l'affectation, qui est le problème, mais l'accès simultané à une seule variable et peu importe comment vous essayez, pour toute implémentation de produire-consommateur, vous devez être capable de le faire (ou le tout sera à un seul fil).

3

Oui. Découvrez la programmation fonctionnelle réactive (PRF), qui est liée à ML concomitant (suggestion de Norman) mais qui est purement fonctionnelle. La sémantique de la FRP est fortement "simultanée" tout en ayant un modèle sémantique simple, précis, déterministe, fonctionnel (fonctions du temps).

Edit: Je cite ici « concurrente », parce que je ne pas dire la notion opérationnelle habituelle (axée sur la mise en œuvre,) de la concurrence, ce qui est impératif et non déterministe, entravant ainsi & pratique raisonnement dependably correct.