Use Where with .Select Linq - linq

I have a scenario where i have to use .Select with where in LINQ.
Below is my query.
List<DTFlight> testList = _ctrFlightList.Select(i => new DTFlight() { AirLineName = i.AirLineName,ArrivalDate = i.ArrivalDate }).ToList();
I want ti use where(add condition) to this query.
Please Help...
Thanks.

I suggest you this use of Where :
List<DTFlight> testList = _ctrFlightList.
Where(ctrFlight => ctrFlight.Property > 0).
Select(i => new DTFlight() { AirLineName = i.AirLineName, ArrivalDate = i.ArrivalDate }).ToList();
Where returns a IEnumerable, so you can apply your Select on it.

Simply add the Where before the Select:
List<DTFlight> testList =
_ctrFlightList.Where(<your condition>)
.Select(i => new DTFlight() { AirLineName = i.AirLineName,
ArrivalDate = i.ArrivalDate })
.ToList();

What is the problem?
List<DTFlight> testList = _ctrFlightList.Where(p => p.ArrivalDate > DateTime.Now).Select(i => new DTFlight() { AirLineName = i.AirLineName,ArrivalDate = i.ArrivalDate }).ToList();
for example... What condition do you need?

Related

What's the equivalent of GROUP INTO in Linq extension method?

This is how I'm filtering and grouping transTasks.
var transTasks = from t in taskData
where t.RangeName == rName
group t by t.CultureID into g
select new { language = g.Key, tasks = g };
Now I've a new requirement. Depending on the conditions, I'may filter by RangeName or by TaskOrderId.
That's why I've transformed the above Linq code to the following;
var transTasks = taskData
.Where(predicate)
.GroupBy(???)
.Select(???);
I've researched but I can't still find the equivalent of group into for the extension method. I need to group those transTasks because there is a loop inside another loop.
Thanks for helping
GroupBy is the equivalent , and it seems you have figured it out, your query in Method Syntax would be:
var transTrasks = taskData.Where(t => t.RangeName == rName)
.GroupBy(t => t.CultureID)
.Select(g => new { language = g.Key, tasks = g });
As a side note, Any LINQ query in query expression compiles to Method Syntax.
var transTasks = taskData
.Where(predicate)
.GroupBy(t => t.CultureID)
.Select(g => new { language = g.Key, tasks = g });

Convert query to lambda

I want to know how can I write this query:
var query = from p in context.DimProduct
from psc in context.DimProductSubcategory
// on psc.ProductCategoryKey equals pc.ProductCategoryKey
where psc.EnglishProductSubcategoryName == subCategoryName
&& psc.ProductSubcategoryKey == p.ProductSubcategoryKey
select new DimProductDTO
{
ProductKey = p.ProductKey,
ProductSubcategoryKey = p.ProductSubcategoryKey,
EnglishProductName = p.EnglishProductName,
Size = p.Size,
StandardCost = p.StandardCost
};
I tried some queries, but no success. My problem is that I don't know how to have access to DimProduct and DimProductSubcategory.
Any suggestions?
context.DimProduct
.SelectMany(p => new { p, psc = context.DimProductSubcategory })
.Where(x => x.psc.EnglishProductSubcategoryName == subCategoryName
&& x.psc.ProductSubcategoryKey == x.p.ProductSubcategoryKey)
.Select(x => new DimProductDTO {
ProductKey = x.p.ProductKey,
ProductSubcategoryKey = x.p.ProductSubcategoryKey,
EnglishProductName = x.p.EnglishProductName,
Size = x.p.Size,
StandardCost = x.p.StandardCost })
However, you're not selecting anything from DimProductSubcategory, so I think the same can be done using Any() extension method:
context.DimProduct
.Where(x => context.DimProductSubcategory
.Any(y => y.EnglishProductSubcategoryName == subCategoryName
&& y.ProductSubcategoryKey == x.ProductSubcategoryKey))
.Select(x => new DimProductDTO {
ProductKey = x.ProductKey,
ProductSubcategoryKey = x.ProductSubcategoryKey,
EnglishProductName = x.EnglishProductName,
Size = x.Size,
StandardCost = x.StandardCost });
It should generate IN SQL statement within the query.
That is not exactly same query, but it produces same result via inner join (I believe that is more efficient than cross join)
context.DimProduct
.Join(context.DimProductSubcategory
.Where(x => x.EnglishProductSubcategoryName == subCategoryName),
p => ProductSubcategoryKey,
psc => ProductSubcategoryKey,
(p,psc) => new { p, psc })
.Select(x => new DimProductDTO {
ProductKey = x.p.ProductKey,
ProductSubcategoryKey = x.p.ProductSubcategoryKey,
EnglishProductName = x.p.EnglishProductName,
Size = x.p.Size,
StandardCost = x.p.StandardCost })
Also your original query can be rewritten as
var query = from p in context.DimProduct
join psc in context.DimProductSubcategory
on p.ProductSubcategoryKey equals psc.ProductSubcategoryKey
where psc.EnglishProductSubcategoryName == subCategoryName
select new DimProductDTO {
ProductKey = p.ProductKey,
ProductSubcategoryKey = p.ProductSubcategoryKey,
EnglishProductName = p.EnglishProductName,
Size = p.Size,
StandardCost = p.StandardCost
};
Generated SQL will look like:
SELECT [t0].[ProductKey], [t0].[ProductSubcategoryKey]
FROM [DimProduct] AS [t0]
INNER JOIN [DimProductSubcategory] AS [t1]
ON [t0].[EnglishProductSubcategoryName] = [t1].[ProductSubcategoryKey]
WHERE [t1].[EnglishProductSubcategoryName] = #p0

Co-related Queries using lambda expressions

How can I convert this LINQ query from query syntax to method syntax? I am performing a co-related query operation.
var query = (from r in objEntities.Employee
where r.Location == (from q in objEntities.Department
where q.Location == r.Location
select q.Location).FirstOrDefault()
select new
{
FirstName = r.FirstName,
LastName = r.LastName,
Age = r.Age,
Location = r.Location
});
GridView1.DataSource = query;
GridView1.DataBind();
I think you are trying to convert the query to method-based query instead of syntax-based query.
var query = objEntities.Employee
.Where(e => e.Location == objEntities.Department
.Where(d => d.Location == r.Location)
.Select(d => d.Location)
.FirstOrDefault())
.Select(e => new {
FirstName = e.FirstName,
LastName = e.LastName,
Age = e.Age,
Location = e.Location
});
I'm also pretty sure your inner expression within where clause could be replaced with something like that:
.Where(e => objEntities.Department.Any(d => d.Location == e.Location)
Nested queries always have performance issue instead you should use join:
In the lambda expression query should be
var query = objEntities.Employee.Join(objEntities.Department, E => E.Location,
D => D.Location,
(E,D) => new {
FirstName = E.FirstName,
LastName = E.LastName,
Age = E.Age,
Location = E.Location
});

How to rewrite it more efficiently (linq with split)?

here is the problem:
I have a column with the topics in the format: "boston | new york | chicago". The names can be different and number of the topics can vary in the records.
What I need to come up with is the collection of the same names with the count of those names.
This is what I have done:
var splitted = queryResult.Select(x => x.TopicData);
List<string> lstOfTopics = new List<string>();
foreach (var element in splitted)
{
string[] splitedTopics = element.Split('|');
lstOfTopics.AddRange(splitedTopics);
}
var groupedTopics = lstOfTopics.GroupBy(x => x).Select(group => new {key = group.Key, count = group.Count()}).AsEnumerable();
seems a lot of code for a simple task. any ideas how to simplify this?
thanks!
You can construct the list using SelectMany and ToList:
List<string> lstOfTopics = splitted.SelectMany(x => x.Split('|')).ToList();
You can also omit the construction of the list entirely:
var groupedTopics = queryResult
.SelectMany(x => x.TopicData.Split('|'))
.GroupBy(x => x)
.Select(group => new { group.Key, Count = group.Count()});
var groups = queryResult
.SelectMany(t => t.TopicData.Split('|')
.GroupBy(n => n)
.Select(g => new { Key = g.Key, Count = g.Count() });
query syntax can be nice and compact:
var topics =
from qr in queryResult
from topic in qr.TopicData.Split('|')
group topic by topic into g
select new { Topic = g.Key, Count = g.Count() };
If you want just the unique topics, but not their counts...
List<string> topicList = topics.Select(item => item.Topic);

LINQ: Group By + Where in clause

I'm trying to implement a T-SQL equivalent of a where in (select ...) code in LINQ.
This is what I have now:
int contactID = GetContactID();
IEnumerable<string> threadList = (from s in pdc.Messages
where s.ContactID == contactID
group 1 by new { s.ThreadID } into d
select new { ThreadID = d.Key.ThreadID}).ToList<string>();
var result = from s in pdc.Messages
where threadList.Contains(s.ThreadID)
group new { s } by new { s.ThreadID } into d
let maxMsgID = d.Where(x => x.s.ContactID != contactID).Max(x => x.s.MessageID)
select new {
LastMessage = d.Where(x => x.s.MessageID == maxMsgID).SingleOrDefault().s
};
However, my code won't compile due to this error for the ToList():
cannot convert from
'System.Linq.IQueryable<AnonymousType#1>'
to
'System.Collections.Generic.IEnumerable<string>'
Anyone have any suggestions on how to implement this? Or any suggestions on how to simplify this code?
Your query returns a set of anonymous types; you cannot implicitly convert it to a List<string>.
Instead, you should select the string itself. You don't need any anonymous types.
Change it to
var threadList = pdc.Messages.Where(s => s.ContactID == contactID)
.Select(s => s.ThreadID)
.Distinct()
.ToList();
var result = from s in pdc.Messages
where threadList.Contains(s.ThreadID)
group s by s.ThreadID into d
let maxMsgID = d.Where(x => x.ContactID != contactID).Max(x => x.MessageID)
select new {
LastMessage = d.Where(x => x.MessageID == maxMsgID).SingleOrDefault()
};

Resources