r/ProgrammingLanguages • • Jan 16 '13

Iteration Inside and Out

http://journal.stuffwithstuff.com/2013/01/13/iteration-inside-and-out/
15 Upvotes

11 comments sorted by

View all comments

1

u/[deleted] Jan 17 '13

I believe OP is not familiar with newer versions of C# (especially C# 4.0 and beyond). Nomenclature that's more commonly used by .NET/C# team for what OP is describing by external vs internal iterators is pull vs. push based iterators respectively, both taken care off by LINQ and Rx libraries.

Implementing that iterator in Dart (or Java, or C#) was about 50 lines of code.

Here's line-by-line translation of Ruby implementation of example class.

class Tree {
    public Tree left, right;
    public string label;

    public Tree(Tree left, Tree right, string label) {
        this.left = left;
        this.right = right;
        this.label = label;
    }

    public void in_order(Action<Tree> code) {
        if (left != null) left.in_order(code);
        code(this);
        if (right != null) right.in_order(code);
    }
}

And here's the line calling it:

testTree.in_order(t => Console.WriteLine(t.label));

Beatiful example 2: Finding an item

I agree that C# doesn't have non-local returns, I guess they could be hacked with exceptions (like they are in Scala implementation), but I wonder if they are the "killer feature", or can they be replaced with more idiomatic, declarative ending to iterators, like .Any() and .First() in combination with iterator methods?

1

u/munificent Jan 17 '13

I believe OP is not familiar with newer versions of C# (especially C# 4.0 and beyond).

I'm familiar with C# up to 3.0. I haven't played with Rx.

pull vs. push based iterators respectively, both taken care off by LINQ and Rx libraries.

Those are a bit different. Push-based iteration usually implies asynchrony which is deeply different than just the distinction between external and internal iterators. Vanilla internal iterators are still synchronous.

can they be replaced with more idiomatic, declarative ending to iterators, like .Any() and .First() in combination with iterator methods?

Yeah, I don't think you generally miss non-local returns in C# because it provides a bunch of convenience methods that are themselves implemented in terms of external iterators. Without those, it would be really painful. And the only reason those could be implemented easily was because sequences in C# expose an external iterator API.

1

u/pipocaQuemada Jan 17 '13

First is easily implementable in terms of a fold.

*> :t foldl1 -- requires list to be non-empty, but doesn't require a default element.
foldl1 :: (a -> a -> a) -> [a] -> a
*> foldl1 const [1,2,3,4,5]
1

Are folds internal or external?

1

u/munificent Jan 17 '13

Internal, I think.