Custom iterator types (methods using yield return
)
#7571
Unanswered
Rekkonnect
asked this question in
Language Ideas
Replies: 2 comments 2 replies
-
Is there a requirement that these user-defined types implement |
Beta Was this translation helpful? Give feedback.
1 reply
-
How do you expect the code to be "lowered"? What is the compiler supposed to do when encountering a using System.Collections.Generic;
static IEnumerable<int> Test()
{
yield return 1;
yield return 2;
} [CompilerGenerated]
internal class Program
{
[CompilerGenerated]
private sealed class <<<Main>$>g__Test|0_0>d : IEnumerable<int>, IEnumerable, IEnumerator<int>, IEnumerator, IDisposable
{
private int <>1__state;
private int <>2__current;
private int <>l__initialThreadId;
int IEnumerator<int>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <<<Main>$>g__Test|0_0>d(int <>1__state)
{
this.<>1__state = <>1__state;
<>l__initialThreadId = Environment.CurrentManagedThreadId;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
}
private bool MoveNext()
{
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<>2__current = 1;
<>1__state = 1;
return true;
case 1:
<>1__state = -1;
<>2__current = 2;
<>1__state = 2;
return true;
case 2:
<>1__state = -1;
return false;
}
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
[DebuggerHidden]
[return: System.Runtime.CompilerServices.Nullable(1)]
IEnumerator<int> IEnumerable<int>.GetEnumerator()
{
if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
{
<>1__state = 0;
return this;
}
return new <<<Main>$>g__Test|0_0>d(0);
}
[DebuggerHidden]
[return: System.Runtime.CompilerServices.Nullable(1)]
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable<int>)this).GetEnumerator();
}
}
private static void <Main>$(string[] args)
{
}
[System.Runtime.CompilerServices.NullableContext(1)]
[IteratorStateMachine(typeof(<<<Main>$>g__Test|0_0>d))]
[CompilerGenerated]
internal static IEnumerable<int> <<Main>$>g__Test|0_0()
{
return new <<<Main>$>g__Test|0_0>d(-2);
}
} What is the compiler supposed to do in your functions? If it's as simple as the following, I doubt the team would consider such a feature. public CustomType Method()
{
yield return 1;
yield return 2;
} public CustomType Method()
{
CustomType result = new();
result.AddYield(1);
result.AddYield(2);
return result;
} |
Beta Was this translation helpful? Give feedback.
1 reply
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Summary
Enable the construction of custom iterator types that replace the need for explicitly using
IEnumerable<T>
.Motivation
Only some interface types can be returned on a method returning with
yield return
:IEnumerable
IEnumerable<T>
IEnumerator
IEnumerator<T>
IAsyncEnumerable<T>
IAsyncEnumerator<T>
This is discouraging for two reasons:
Design
We would have an API similar to async method state machine builders, exposing the necessary attributes and classes for designing a type as capable of being returned in a method containing
yield return
.The exact details are not reported here.
Examples
Using a custom enumerable would simply allow you to return a different type in the method, like in the below example:
Effects
Potentially we can design custom types for enumerating nested collections, like two- or three-level nesting which would be the most common. For example:
Beta Was this translation helpful? Give feedback.
All reactions