Linq using sum() in list within a list - c#

The relationship between them is one order to many journals. Now I want to get the sum of all pending orders (or records that are flagged as false under IsDelivered in Order entity).
So far, I have this query but can't seem to get working when I add .Sum()
Orders
.Where(o => o.IsDelivered == false)
.Select(o => new {
pendingOrders = o.Journals.Sum(j => j.TotalAmount)
})
So far this results to:
In a nutshell, how can I get the sum of them? If query needs to be altered or should be a new one. It is welcome. Any help would be much appreciated. Thanks!

You can do it in several ways:
You could add Sum(n => n.pendingOrders) to the end of your query to add up the values, or
You could use SelectMany before Select, and use Sum instead of Select.
Either of the two approaches is going to work.

In this case, it is easiest to use SelectMany (MSDN) to flatten your collections, then use Sum:
Orders.Where(o => !o.IsDelivered).SelectMany(o => o.Journals).Sum(j => j.TotalAmount);

Related

How to group records in Entity Frameworkk with where clause

i want to apply where clause on COLID column and wish to take the very last value w.r.t that COLID, e.g in COLID 1 case the last returned value should not be NULL and in COLID 2 it would be 30, against each ENTRYID
I can do it well in SQL, look at the query and data:
You can edit your question to append code rather than pasting it into comments. Paste the code into the question and use the "{}" button in the editor to code format.
You can group and sort items in Linq without too much issue.
context.Entries
.GroupBy(x => x.EntryID)
.Select(x => x.OrderByDescending(y => y.ColID).FirstOrDefault())
.ToList();
GroupBy defines what columns make up the unique grouping. In your case if you want the latest Entry then the EntryId would be enough to define what to group on. This will form the Key for each group. From there we use Select to tell it what to select from each group. The group will be all entries of that EntryID so we order by the ColID descending so the biggest one is first, then use FirstOrDefault to take the largest one. The ToList() at the end materializes the result to retrieve the latest ColID version of each EntryID.
Edit: If you want to only consider non-null values:
context.Entries
.Where(x => x.ColValueId != null)
.GroupBy(x => x.EntryID)
.Select(x => x.OrderByDescending(y => y.ColID).FirstOrDefault())
.ToList();
Linq is a bit different than SQL and can have some limitations when used with EF because EF will ultimately need to convert it to SQL. Still, it is well worth reading up on Linq because it is a very powerful tool when working with objects and it allows EF to do a lot of the heavy lifting.

Using linq to retrieve distinct dates

Hi I'm having trouble retrieving distinct dates from a database. In this database I have several events on any particular day and results show a list of events with the same date / 'StartDate' field. How could I retrieve just the distinct days. I've tried:
ICollection result;
result= client.GetEventInstances().Select(x => x.StartDate).Distinct();
I expect to see just one distinct date along with just the first event for that date only.
Then you need to group on the events and get the first item out of every date:
client.GetEventInstances()
.GroupBy(k => k.StartDate.Date)
.ToDictionary(k => k.Key, v => v.First())
Well, I managed to search and find a solution for my needs, it wont suit everyone of course. Thanks for the time people gave me on this, always appreciated
ICollection<EventInstance> result;
result = client.GetEventInstances();
IEnumerable<EventInstance> distinctDate = result
.GroupBy(e => e.StartDate.Date)
.Select(group => group.First());

How can I check whether an item of an Entity's child collection exists in another collection with LINQ to Entities?

I hope that somebody caught the idea from the question, but I didn't know how to summarize it better.
The thing is I try to make a simple search in an application. I have Question and Tag entities, like these in StackOverflow - in a many-to-many relationship.
I pass an array of tag IDs to my filtering method. It should return all the Question entities that have this tags (with this IDs). I did it like this:
int[] tagIds = { 1, 2, 3};
var questions = myEntities.Questions
.ToList()
.Where(q => tagIds.Intersect(q.Tags.Select(t => t.Id).ToArray()).Any())
.ToList();
Everything worked fine, but now I added more filters and more methods use this filter, so I want to get a DbQuery object, instead of a List.
I tried removing the .ToList() expressions, to get the appropriate result:
int[] tagIds = { 1, 2, 3};
var questions = myEntities.Questions
.Where(q => tagIds.Intersect(q.Tags.Select(t => t.Id).ToArray()).Any());
Unfortunatelly, I get an exception, stating that LINQ does not recognize the .ToArray() method. Can anyone give me a better idea how to achieve this?
The ToArray() method isnt even needed in
.Where(q => tagIds.Intersect(q.Tags.Select(t => t.Id).ToArray())
because Intersect just needs an IEnumerable that Select already returns and not necessarily an array.

LINQ query OrderBy doesn't work

_db.InstellingAdressens
.Where(l => l.GEMEENTE.Contains(gem_query))
.OrderBy(q => q.GEMEENTE)
.Select(q => q.GEMEENTE)
.Distinct();
this is the query. it returns a List<string> but the strings are not ordered at all. Why does the OrderBy have no effect? and how to fix it?
Try putting OrderBy at the end of your call.
_db.InstellingAdressens.
Where(l => l.GEMEENTE.Contains(gem_query)).
Select(q=>q.GEMEENTE).Distinct().
OrderBy(q=>q).ToList();
Distinct has no knowledge that you have ordered your items before it gets them, so it can't use that knowledge. As such, it has to assume the items are unordered, and will thus just do what it wants with them.
A typical implementation will use a hashtable, which isn't ordered by what you normally want the items to be ordered by, so the result from the distinct operation is an unordered set.
So as others have suggested, change the ordering of your calls to do the ordering last, and you should get what you want.
Change the order of calls
_db.InstellingAdressens.Where(l => l.GEMEENTE.Contains(gem_query)).Select(q=>q.GEMEENTE).Distinct().OrderBy(q=>q.GEMEENTE).ToList();
Try this just put orderby last of the query
_db.InstellingAdressens
.Where(l => l.GEMEENTE.Contains(gem_query))
.Select(q=>q.GEMEENTE)
.Distinct()
.OrderBy(q=>q.GEMEENTE).ToList();

LINQ: Getting the row with the maximum value of a given attribute

I have a bunch of rows grouped on an attribute called MyID. Now I want the one row from each group where the StatusDate attribute is the highest in that one group.
This is what I've come up with.
rows.Select(x => x.Where(y => y.StatusDate == x.Max(z => z.StatusDate)).First())
With a bit more explanation:
rows.Select(x => // x is a group
x.Where(y => // get all rows in that group where...
// the status date is equal to the largest
// status date in the group
y.StatusDate == x.Max(z => z.StatusDate)
).First()) // and then get the first one of those rows
Is there any faster or more idiomatic way to do this?
One alternative would be to use:
rows.Select(x => x.OrderByDescending(y => y.StatusDate).First());
... and check that the query optimiser knows that it doesn't really need to sort everything. (This would be disastrous in LINQ to Objects, but you could use MaxBy from MoreLINQ in that case :)
(Apologies for previous version - I hadn't fully comprehended the grouping bit.)
Don't know if this is Linq to SQL, but if it is, you could alternatively accomplish via a rank() function in SQL (rank each group by date, then select the first ranked row from each), then call this as a stored proc from LINQ. I think that's an approch that is becoming more idiomatic as people hit the bounderies of LINQ2SQL...

Categories