1

I am not sure why the "not all code paths return a value" error appears (see commented code below). Is it because the foreach loop is considered as not one path but many, and it's possible that an iteration might not return a value and yet the loop would continue?

[BTW, my goal is to process 100K urls, creating many web requests so they are active simultaneously, and be able to capture the status of each url (alive, moved, timed out) while updating the UI as the set of urls is being processed with real-time information about the number of bad urls found so far and the number or urls processed so far. I've tried Parallel.ForEach approach with synchronous web requests but the UI became unresponsive.]

EDITED to include a test if Rows.Count == 0.

  public async Task<UrlInfo> ProcessUrls(DataTable urls)
    {


     if (urls.Rows.Count == 0)
        {
            return new UrlInfo();
        }
        else

      {


        foreach (DataRow r in urls.Rows)
        {

            UrlInfo info = new UrlInfo()
                {
                    Url = (string)r["url"],
                    status = UrlStatusCode.untested,
                    articleid = (int)r["articleid"]
                };

               return await Foo(info);                  
         }

     }
        //return new UrlInfo();  // error unless this line is uncommented
    }



      public async Task<UrlInfo> Foo(UrlInfo info) {

        <snip>
      }
Artless
  • 4,522
  • 1
  • 25
  • 40
Tim
  • 8,669
  • 31
  • 105
  • 183
  • http://stackoverflow.com/questions/17992553/concept-behind-these-4-lines-of-tricky-c-code –  Aug 03 '13 at 15:50

1 Answers1

2

The compiler is complaining about the situation where urls.Rows does not contain any elements. In that case, the method will never encounter a return statement.

On a side note, I do not think that method means what you think it means. A method only returns once, so it would only process the first url.

Stephen Cleary
  • 437,863
  • 77
  • 675
  • 810
  • If I test for the condition where Rows.Count == 0 (see edited code) the compiler still complains. Also, I don't follow your side note. Is it not possible to execute an async method inside a loop, so that it is in effect called multiple times, and keep track of which invocation is returning by passing a callback or delegate to the async method? I'm hoping to do someting like that. How to issue multiple web requests simultaneously or in parallel and keep track of responses? – Tim Aug 03 '13 at 16:11
  • @Tim The compiler does not and cannot know that if `Rows.Count != 0`, `foreach` will always execute at least once. C# is designed so that it's not the compiler's job to make that determination, it's your job as the programmer to write the code in such a way that the compiler doesn't have to make that determination. –  Aug 03 '13 at 16:19
  • @Tim: It is certainly possible to call an `async` method from within a loop. However, your loop is returning before it proceeds to the next iteration of the loop. – Stephen Cleary Aug 04 '13 at 00:42
  • LOL, Stephen. I am so weary of going in circles on this myself, that I must have subconsciously overlooked that `return await`. Eager to break out of the circle myself. Duh :-) – Tim Aug 04 '13 at 12:29