I want to run a linq query that will return values to my custom DTO. This particular linq query will need to take into account joins from multiple tables, using switch case statements, count (*) and group by
This is the SQL version sample of the query I will need a LinQ equivalent of...
select
slm.SLType,
count(c.EStatID) as EStat,
COUNT(cpd.TrId) as Training,
COUNT(
CASE WHEN cpd.TrStat= 44 THEN 1
WHEN cpd.TrStat!= 44 THEN NULL
WHEN cpd.TrStat IS NULL THEN NULL
END) as TrainingComplete,
COUNT(
CASE WHEN cpd.CndAssess = 44 THEN 1
WHEN cpd.CndAssess != 44 THEN NULL
WHEN cpd.CndAssess IS NULL THEN NULL
END) as AssessmentComplete
from TabC c , TabCPD cpd, TabSLM slm
where cpd.SLid = slm.SLid
and c.Id= cpd.CID
and c.O_Id = 1
group by slm.SLType
It returns records in the following format. I have put each record as a new line with fields separated by commas. The numbers below are just as an example
TypeA, 0 , 1 , 1, 0
TypeB, 1 , 0 , 1, 0
I am trying to create a linq query in the format like the one below without much luck
var query =
from c in TabC, ......
select new MyCustomTableC_DTO
{
DTOproperty = c.MatchingTable property,....
}
MyCustomTableC_DTO will have a property for each field in the query. Any idea how to accomplish this? The query I will use to build a list of type MyCustomTableC_DTO
Thanks for your time...
When you try to convert that SQL statement to LINQ line by line, you would get something like this:
from row in (
from c in db.TabC
from cpd in db.TabPD
from slm in db.TabSLM
where cpd.SLid == slm.SLid
where c.Id == cpd.CID
where c.O_Id == 1
select new { c, cpd, slm })
group row in row.slm.SLType into g
select new
{
SLType = g.Key,
EStat = g.Count(r => r.c.EstatID != null),
Training = g.Count(r => r.cpd.TrId != null),
TrainingComplete =
g.Count(r => r.cpd.TrStat == 44),
AssessmentComplete =
g.Count(r => r.cpd.CndAssess == 44)
};
This query however, over complicates things and completely ignores that fact that Entity Framework knows much more about the model and generates all foreign keys as properties on the entities. Besides that, with LINQ, you must often approach things the other way around. In your case for instance, don't start with the TabC
or TabSLM
entity, but TabPD
, since that table is the cross-table. With this knowledge, we can write the LINQ query like this:
from cpd in db.TabCPDs
where cpd.TabC.O_Id == 1
group cpd by cpd.TabSLM.SLType into g
select new
{
SLType = g.Key,
EStat = g.Count(r => r.TabC.EstatID != null),
Training = g.Count(r => r.TrId != null),
TrainingComplete =
g.Count(r => r.TrStat == 44),
AssessmentComplete =
g.Count(r => r.CndAssess == 44)
};
This is much simpler and (if I'm not mistaking) has the same result.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.