yield iteration

anonymous anonymous at example.com
Sun Jul 29 06:39:00 PDT 2012


A subthread of the "Impressed" thread revolved around D's lack of 
a yield mechanism for iteration.
Nick Sabalausky mentioned his earlier attempt to create a library 
based yield which unfortunately was too slow to compete with 
explicit opApply/ranges [1].

I took a shot at it. It's fast. The resulting code is reasonably 
pretty. But it doesn't provide a range interface, just opApply.

---
module yielder;

import core.thread;

/**
	Examples:
	---
	import yielder;
	import std.stdio;
	
	auto y = new class Yielder!int {
		final void yielding() {
			yield(0);
			yield(13);
			yield(42);
		}
	};
	
	foreach(x; y) {
		writeln(x);
	}
	---
*/
class Yielder(E) {
	abstract void yielding();
	
	this() {
		this.fiber = new Fiber(&yielding);
	}
	
	private {
		Fiber fiber;
		int result;
		int delegate(ref E) callback;
	}
	
	final int opApply(int delegate(ref E) cb) {
		callback = cb;
		result = 0;
		fiber.reset();
		fiber.call();
		return result;
	}
	
	final void yield(ref E value) {
		result = callback(value);
		if(result != 0) {
			Fiber.yield();
		}
	}
	final void yield(E value) {
		yield(value);
	}
}
---

[1] 
https://semitwist.com/articles/article/view/combine-coroutines-and-input-ranges-for-dead-simple-d-iteration



More information about the Digitalmars-d mailing list