I have a list of int? that can have 3 different values: null, 1, and 2.
I would like to know which of them occurs the most in my list. To group them by value I tried to use:
MyCollection.ToLookup(r => r)
How can I get the value with most occurrence?
You don't need a Lookup, a simple GroupBy would do:
var mostCommon = MyCollection
.GroupBy(r => r)
.Select(grp => new { Value = grp.Key, Count = grp.Count() })
.OrderByDescending(x => x.Count)
.First()
Console.WriteLine(
"Value {0} is most common with {1} occurrences",
mostCommon.Value, mostCommon.Count);
Related
var entity = await _abcRepository.get(Id);
var X = entity.GroupBy(c => c.number).Where(grp => grp.Count() == 1).Take(10).ToList();
in images you see [0] and inside of it one more [0].
How can I get that model value.
X[0][0] is not working.
X.Value is not working.
I need to convert that dictionary to model.
Use .Select to normalize aggregation as per your wish.
var X = entity.GroupBy(c => c.number).Where(grp => grp.Count() == 1)
.Select(group => new { GroupKey = group.Key, Items = group.ToList() })
.Take(10).ToList();
You could try something like this:
var entity = await _abcRepository.get(Id);
var results = entity.GroupBy(c => c.number)
.Where(grp => grp.Count() == 1)
.Take(10)
.ToDictionary(grp => grp.Key, grp => grp.First());
Essentially, the lambda you pass in Where method certifies that the groups are created contains only one item. That being said, you can use the First on each group to fetch that one element.
I am currently getting error in my grouping logic. I am trying to sum the values in EMV for productnames that are same. I am getting error while passing only some list. How do I avoid this exception. I am not aware of doing null checks in linq experssion
System.ArgumentNullException: 'Value cannot be null. Parameter name: key'
Code
public Dictionary<string, decimal> SumProductEmv(IEnumerable<FirmWideAllocationsViewModel> allProducts)
{
if (allProducts == null)
return null;
return allProducts
.GroupBy(product => product.ProductName)
.Select(group => new
{
ProductName = group.Key, // this is the value you grouped on - the ProductName
EmvSum = group.Sum(item => item.Emv)
})
.ToDictionary(x => x.ProductName, x => x.EmvSum);
}
You could filter null or empty keys out using Where, try this:
return allProducts
.Where(product => !string.IsNullOrEmpty(product.ProductName))
.GroupBy(product => product.ProductName)
.Select(group => new
{
ProductName = group.Key, // this is the value you grouped on - the ProductName
EmvSum = group.Sum(item => item.Emv)
})
.ToDictionary(x => x.ProductName, x => x.EmvSum);
Also, you could Distinct() to prevent ArgumentException: An element with the same key already exists in the dictionary but then you need to decide which element you want to take, first, last, etc.
Having this Linq query which returns grouping of 4 DateTime:
IEnumerable<IGrouping<DateTime, QuoteSnapshotModel>> lista = (from q in quoteModeList
where q.QuoteTradeType == "Q"
select q).GroupBy(n => n.ExceriseDate);
How can I order the groups by DateTime and get only the first group?
meaning **List<QuoteSnapshotModel>**
Also, how can I get only the second List<QuoteSnapshotModel> (according to DateTime)
Try this:
for this you have to create a list<QuoteSnapshotModel> within class QuoteSnapshotModel.
int record = 1;
List<QuoteSnapshotModel> result =
quoteModeList
.Where(x => x.QuoteTradeType == "Q")
.GroupBy(x => x.ExceriseDate,
(a, b) => new QuoteSnapshotModel
{
ExceriseDate = a,
ListQuoteSnapshotModel = b.ToList()
})
.OrderByDescending(t => t.ExceriseDate)
.Skip(record - 1).Take(1).ToList();
Update
You can use only the first group
List<QuoteSnapshotModel> list =quoteModeList.Where(x=>x.QuoteTradeType =="Q")
.GroupBy(x => x.ExceriseDate)
.OrderBy(x=>x.Key)
.FirstOrDefault().Select(x=>x.QuoteTradeType).ToList();
You can use only the second group
List<QuoteSnapshotModel> list =quoteModeList.Where(x=>x.QuoteTradeType =="Q")
.GroupBy(x => x.ExceriseDate)
.OrderBy(x=>x.Key)
.Skip(1).First().Select(x=>x.QuoteTradeType).ToList()
How can I order the groups by DateTime
.OrderBy(g => g.Key) or .OrderBy(g => g.First().ExerciseDate)
and get only the first group?
.First() (or .FirstOrDefault() if it's possible there are 0 groups)
how can I get only the second List (according to DateTime)
.Skip(1).Take(1) or .ElementAt(1) or .Skip(1).First()
Putting it all together:
IEnumerable<IGrouping<DateTime, QuoteSnapshotModel>> lista = (
from q in quoteModeList
where q.QuoteTradeType == "Q"
select q
).GroupBy(n => n.ExerciseDate);
IList<QuoteSnapshotModel> firstQuote = lista.OrderBy(x => x.Key).Select(x => x.ToList()).FirstOrDefault();
IList<QuoteSnapshotModel> secondQuote = lista.OrderBy(x => x.Key).Skip(1).Select(x => x.ToList()).FirstOrDefault();
I want to get the duplicate values count from one table. The input values are like as below,
SUB -xxx-20160721
SUB -xxx-20160721
SUB -125-20160022
Here (1) and (2) are same value. If the Name is more than 1 it should return 1 as a result. the result should return the count as (2).
var numberOfDuplicates = this.UnitOfWork.Repository<Models.SUB>()
.Queryable().GroupBy(x => x.Name)
.Where(x => x.Count() > 1)
.Select(x => x.Count());
The result is
2
2
2
2
2
3
2
2
4
Please guide me on this..
The return value of the below code is an anonymous object with 2 properties:
Value The value that is duplicate
Amount The amount of times it is duplicate
var numberOfDuplicates = this.UnitOfWork.Repository()
.Queryable().GroupBy(x => x.Name)
.Where(x => x.Count() > 1)
.Select(x => new { Value = x.Key, Amount = x.Count() } );
The problem with your code is that you're returning the Count of each group using the Select(x=> x.Count()) statement.
You can return the Name (The Key of Grouping) and the Count using anonymous types:
var numberOfDuplicates = this.UnitOfWork.Repository<Models.SUB>()
.Queryable().GroupBy(x => x.Name)
.Where(x => x.Count() > 1)
.Select(x => new { Name = x.Key, Count = x.Count() });
foreach(var dup in numberOfDuplicates)
{
Console.WriteLine($"Name = {dup.Name } ** Counter = {dup.Count}");
}
Results:
Name = 1.SUB -xxx-20160721 ** Count = 2
I have a list Having multiple Items and 3 props ID,DATE,COMMENT.ID field is Auto incremented in DATABASE.
Let say list Contains
2,16AUG,CommentMODIFIED
1,15AUG,CommentFIRST
3,18AUG,CommentLASTModified
I want to get a single ITEM.Item Having Minimum DATE and having Latest Comment. In this case
1,15AUG,CommentLASTModified
Any easy way to do it using LINQ.
orderedItems = items.OrderBy(x => x.Date);
var result = items.First();
result.Comment = items.Last().Comment;
To get a single item out of the list, you can order the items then take the first one, like this:
var result = items
.OrderByDescending(x => x.Date)
.First();
But First will throw an exception if the items collection is empty. This is a bit safer:
var result = items
.OrderByDescending(x => x.Date)
.FirstOrDefault();
To get the min / max of different columns you can do this:
var result =
new Item {
Id = 1,
Date = items.Min(x => x.Date),
Comment = items.Max(x => x.Comment)
};
But this will require two trips to the database. This might be a bit more efficient:
var result =
(from x in items
group x by 1 into g
select new Item {
Id = 1,
Date = g.Min(g => g.Date),
Comment = g.Max(g => g.Comment)
})
.First();
Or in fluent syntax:
var result = items
.GroupBy(x => 1)
.Select(g => new Item {
Id = 1,
Date = g.Min(g => g.Date),
Comment = g.Max(g => g.Comment)
})
.First();