A little of coordination for Rosettacode

Ali Çehreli acehreli at yahoo.com
Tue Feb 25 22:06:17 PST 2014


On 02/25/2014 03:48 PM, bearophile wrote:
> Is someone willing to write a D entry for this?
>
> http://rosettacode.org/wiki/Rendezvous
>
> Bye,
> bearophile

I think the following satisfies the requirements. Improve at will! :p

import std.stdio;
import std.exception;
import std.array;
import std.concurrency;
import std.datetime;
import core.thread;

class OutOfInk : Exception
{
     this()
     {
         super("Out of ink.");
     }
}

struct Printer
{
     string id;
     size_t ink;

     void print(string line)
     {
         enforce(ink != 0, new OutOfInk);
         writefln("%s: %s", id, line);
         --ink;
     }
}

struct PrinterRendezvous
{
     Printer[] printers;

     void print(string[] lines) shared
     {
         Exception savedException;

         while (true) {
             if (lines.empty) {
                 break;
             }

             if (printers.empty) {
                 // No more printers to try
                 assert(savedException !is null);
                 throw savedException;
             }

             try {
                 synchronized {
                     (cast(Printer)printers.front).print(lines.front);
                 }
                 lines.popFront();

                 // Increase the chance of interleaved output
                 Thread.sleep(10.msecs);

             } catch (OutOfInk exc) {
                 savedException = exc;

                 synchronized {
                     // Switch to the next printer
                     printers = printers[1..$];
                 }
             }
         }
     }
}

void humptyDumptyTask(ref shared(PrinterRendezvous) rendezvous)
{
     auto humptyDumpty = [ "Humpty Dumpty sat on a wall.",
                           "Humpty Dumpty had a great fall.",
                           "All the king's horses and all the king's men,",
                           "Couldn't put Humpty together again.", ];

     rendezvous.print(humptyDumpty);
}

void motherGooseTask(ref shared(PrinterRendezvous) rendezvous)
{
     auto motherGoose = [ "Old Mother Goose,",
                          "When she wanted to wander,",
                          "Would ride through the air,",
                          "On a very fine gander.",
                          "Jack's mother came in,",
                          "And caught the goose soon,",
                          "And mounting its back,",
                          "Flew up to the moon.", ];

     rendezvous.print(motherGoose);
}

void main()
{
     auto rendezvous = shared(PrinterRendezvous)([ Printer("main", 5),
                                                   Printer("reserve", 5) ]);

     spawn(&humptyDumptyTask, rendezvous);
     spawn(&motherGooseTask, rendezvous);
}

Sample output:

main: Humpty Dumpty sat on a wall.
main: Old Mother Goose,
main: Humpty Dumpty had a great fall.
main: When she wanted to wander,
main: All the king's horses and all the king's men,
reserve: Would ride through the air,
reserve: Couldn't put Humpty together again.
reserve: On a very fine gander.
reserve: Jack's mother came in,
reserve: And caught the goose soon,
deneme.OutOfInk at deneme.d([...]): Out of ink.

Ali



More information about the Digitalmars-d-learn mailing list