views:

102

answers:

3

I have a collection of data that checks if there is a change in a particular field to get the sum for another column.

Total = Details.Where(s=>s.indicator != *prior indicator before this...).Sum(s => s.amount);
+1  A: 

I dont think that LINQ by itself can get you the state of the data before it was changed. What I guess you could do is to set an event when the data is about to change (OnChanging) and subscribe to that event, then you would send the amount before the change on the event's parameter.

Now if you want to do all of this in a LINQ-ish way, you should check out the Rx (Reactive) API that MS is working on, its all about using events in a LINQ way.

If you are using a collection that notifies you of the change in the element.. then there might be a parameter being passed that tells you the data that changed.

Francisco Noriega
+1  A: 

You could use a partial class and then use the OnFIELDChanging event to detect the change and call an event elsewhere.

So if you have a User table in your .dbml file which has a property called say FirstName then you could create another class like this;

public partial class User
{
    partial void OnFirstNameChanging(string value)
    {
    }
}

The value passed over is the new value the property is changing to.

Does this help or am I off base with regards to your requirements?

griegs
I think this points me in the right direction thanks!
A: 

If you have two collcection of data you could use the zip method (.Net 4.0) like so

var Total = currentData.Zip(previousData,(current,previous) => current.indicator != previous.indicator ? current.amount : 0).Sum();

if you don't use .net 4.0 you could use this implementation of zip :

static class Enumerable 
{ 
 public static IEnumerable<TResult> Zip<TFirst, TSecond, TResult>(this IEnumerable<TFirst> first, IEnumerable<TSecond> second, Func<TFirst, TSecond, TResult> func) 
 { 
  var ie1 = first.GetEnumerator(); 
  var ie2 = second.GetEnumerator();

  while (ie1.MoveNext() && ie2.MoveNext()) 
   yield return func(ie1.Current, ie2.Current); 
 } 
}

source

Johnny Blaze