Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C#: yield return within a foreach fails - body cannot be an iterator block

Tags:

iterator

yield

c#

Consider this bit of obfuscated code. The intention is to create a new object on the fly via the anonymous constructor and yield return it. The goal is to avoid having to maintain a local collection just to simply return it.

public static List<DesktopComputer> BuildComputerAssets() {                List<string> idTags = GetComputerIdTags();      foreach (var pcTag in idTags)     {         yield return new DesktopComputer() {AssetTag= pcTag                                           , Description = "PC " + pcTag                                           , AcquireDate = DateTime.Now                                            };     }             } 

Unfortunately, this bit of code produces an exception:

Error 28 The body of 'Foo.BuildComputerAssets()' cannot be an iterator block because 'System.Collections.Generic.List' is not an iterator interface type

Questions

  • What does this error message mean?
  • How can I avoid this error and use yield return properly?
like image 248
p.campbell Avatar asked Mar 10 '10 01:03

p.campbell


2 Answers

You can only use yield return in a function that returns an IEnumerable or an IEnumerator, not a List<T>.

You need to change your function to return an IEnumerable<DesktopComputer>.

Alternatively, you can rewrite the function to use List<T>.ConvertAll:

return GetComputerIdTags().ConvertAll(pcTag =>      new DesktopComputer() {         AssetTag    = pcTag,         Description = "PC " + pcTag,         AcquireDate = DateTime.Now     }); 
like image 141
SLaks Avatar answered Sep 21 '22 15:09

SLaks


Your method signature is wrong. It should be:

public static IEnumerable<DesktopComputer> BuildComputerAssets() 
like image 32
Brian Genisio Avatar answered Sep 19 '22 15:09

Brian Genisio