www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - Fibers and Ranges

reply Freddy <Hexagonalstar64 gmail.com> writes:
---
import core.thread;
import std.conv;
import std.stdio;

void formatStuff(P)(P put, int stuff)
{
     put("a");
     put("b");
     put("c");
     put(stuff);
     foreach (i; 0 .. 10)
     {
         put(i ^^ stuff);
     }
}

auto formatRange(alias sub, T...)(T args)
{
     class FormatFiber : Fiber
     {
         string front_;
         this()
         {
             super(&run);
             popFront;
         }

         void run()
         {
             sub(this, args);
         }

         void opCall(T)(T t)
         {
             front_ = t.to!string;
             yield;
         }

         void popFront()
         {
             call;
         }

      property:
         string front()
         {
             return front_;
         }

         bool empty()
         {
             return state != State.HOLD;
         }
     }

     return new FormatFiber;
}

void main()
{
     writeln(formatRange!formatStuff(5));
}
---
Another Idea thoughts?
Oct 04 2015
parent =?UTF-8?Q?Ali_=c3=87ehreli?= <acehreli yahoo.com> writes:
On 10/04/2015 04:40 PM, Freddy wrote:
 ---
 import core.thread;
 import std.conv;
 import std.stdio;

 void formatStuff(P)(P put, int stuff)
 {
      put("a");
      put("b");
      put("c");
      put(stuff);
      foreach (i; 0 .. 10)
      {
          put(i ^^ stuff);
      }
 }

 auto formatRange(alias sub, T...)(T args)
 {
      class FormatFiber : Fiber
      {
          string front_;
          this()
          {
              super(&run);
              popFront;
          }

          void run()
          {
              sub(this, args);
          }

          void opCall(T)(T t)
          {
              front_ = t.to!string;
              yield;
          }

          void popFront()
          {
              call;
          }

       property:
          string front()
          {
              return front_;
          }

          bool empty()
          {
              return state != State.HOLD;
          }
      }

      return new FormatFiber;
 }

 void main()
 {
      writeln(formatRange!formatStuff(5));
 }
 ---
 Another Idea thoughts?
There is std.concurrency.Generator to expose yielded elements as a range: import core.thread; import std.conv; import std.stdio; import std.concurrency; alias FiberRange = std.concurrency.Generator; void yieldString(T)(T arg) { yield(arg.to!string); } void formatStuff(int stuff) { yieldString("a"); yieldString("b"); yieldString("c"); yieldString(stuff); foreach (i; 0 .. 10) { yieldString(i ^^ stuff); } } void main() { auto stuff = new FiberRange!string(() => formatStuff(5)); writeln(stuff); } Ali P.S. D.learn might be a better newsgroup for this thread. :)
Oct 04 2015