0

I'm having a bit of trouble selecting from a data table using LINQ. The results would map to a class TabResult. The class looks like this:

public class TabResult
{
    public decimal Value;
    public string LineNumber;
}

Now I'm trying to add these results to an array of IEnumerable<TabResult>, one index of the array per sheet.

This was my first attempt in code:

public LCRResultSet(DataTable results)
{
    for (int i = 0, sheet = 72; i < 3; i++, sheet++)
    {
        _results[i] = from tab in results.AsEnumerable()
                      where tab.Field<string>("LCR_SHEET_NUMBER") == sheet.ToString()
                      select new TabResult { LineNumber = tab.Field<string>("LCR_LINE_NUMBER"), Value = tab.Field<decimal>("VALUE") };
    }
}

It works okay for the first iteration, _results[0] having the number of values I expect, however the second iteration causes _results[0] to be the same as _results[1], and the third iteration causes _results[0] and _results[1] to be the same as _results[2]. It works okay when I write the 3 queries separately, however I'd prefer to do it this way.

Is there something I missed about LINQ and datatables? Thanks in advance.

Edit 1: A few comments suggested that sheet was being captured as a constant, however, I don't see how this could be as the variable was being incremented each iteration, but the results of previous iterations are being overwritten by the latest iteration. Here is a link to an imgur album showing the watch window after each iteration.

Robert Woods
  • 350
  • 1
  • 6
  • 17
  • I agree with @ASh. My guess would be that sheet has been captured as a constant the first time around. Try moving it into the inner scope of the for loop. – Clint Jul 18 '16 at 13:43
  • Okay, let me give that a go and get back to you. – Robert Woods Jul 18 '16 at 13:44
  • No this didn't fix my problem, I will edit the original question showing this. I would appreciate it if the relevant person would reopen my question. – Robert Woods Jul 18 '16 at 13:54
  • @robert.woods, did you try to copy `sheet` value in a loop? `int copy = sheet; ` and then use it in a predicate? `where tab.Field("LCR_SHEET_NUMBER") == copy.ToString()` – ASh Jul 18 '16 at 14:06
  • @ASh Yes I did, however it is still happening. [Here](https://gfycat.com/EllipticalOldIguanodon) is a gif of me stepping through the debugger. – Robert Woods Jul 18 '16 at 14:21
  • 1
    @robert.woods, all predicates (`where tab.Field("LCR_SHEET_NUMBER") == sheet.ToString()`) use the same captured `sheet` variable. you need to make the 3rd variable with current value. `for (int i = 0, sheet = 72; i < 3; i++, sheet++) { int copy = sheet; _results[i] = from tab in results.AsEnumerable() where tab.Field("LCR_SHEET_NUMBER") == copy.ToString() select new TabResult { LineNumber = tab.Field("LCR_LINE_NUMBER"), Value = tab.Field("VALUE") }; }` – ASh Jul 18 '16 at 14:31
  • @ASh It works now, thank you for your patience. – Robert Woods Jul 18 '16 at 14:36
  • 1
    @robert.woods, another option in this situation is to project result immediately (apply `.ToList()` or `.ToArray()`) and avoid deferred execution pitfalls – ASh Jul 18 '16 at 14:40

0 Answers0