Draco-lang / Language-suggestions

Collecting ideas for a new .NET language that could replace C#
75 stars 5 forks source link

Loops as expressions for sequences #32

Open LPeter1997 opened 2 years ago

LPeter1997 commented 2 years ago

It came up in a discussion that since most control structures will return a value, we could also define some sensible evaluation value for loops too. There are two semantics that are sensible enough to consider (at least the ones we could think of) + the usual, safe defaults:

Singular return value

This would be what Rust does. The loop evaluates to a single value. In Rust this is only valid in the loop construct (infinite loop) and every break has an associated return value. Here is an example.

Sequential return value

This would essentially be implicit generators. Something like this:

println(string.Join(",", for i in 0:5 do i * i));

Could print 0, 1, 4, 9, 16.

This brings up a few questions, for example will this make the loop essentially lazy? What will the following piece of code do?

val squares = for i in 0:5 do { println("a"); i * i };

Will this immediately print the 5 as or only when squares is enumerated? Wouldn't this behavior be too misleading?

Evaluate to unit

The simplest semantic would be that all loops simply evaluate to unit. This means they can still be used where expressions can (like in arrow-bodied methods), but their result is essentially meaningless.

Binto86 commented 2 years ago

In the seqential return value case we should just allow the result to implement IEnumerable and then every time it loops it would do everything and then it would add the last expresion to the collection which will be returned E. g.

var array=for(var i=0; i<5; i++) { 
println("a"); //prints a every time before it eveluates i*i
i*i
}