How do I convert this query into LINQ? - linq

SELECT *
FROM
ProcedureLookup ProcLookup
INNER JOIN (SELECT PatientProcedures.PP_ProcedureId, COUNT(*) as ProcCount
FROM (PatientProcedures INNER JOIN Treatments ON PatientProcedures.PP_TreatmentId = Treatments.TS_TreatmentId)
WHERE YEAR(Treatments.TS_Date) = YEAR(GETDATE())
GROUP BY PatientProcedures.PP_ProcedureId) cyearProc ON ProcLookup.PL_ProcedureId = cyearProc.PP_ProcedureId
ORDER BY ProcCount DESC;
Here ProcedureLookup, Treatments, PatientProcedures are the tables.

Here linq query.
var result = (from ProcLookup in db.ProcedureLookup
join cyearProc in (
from p in db.PatientProcedures
join t in db.Treatments on p.PP_TreatmentId equals
t.TS_TreatmentId
where
t.TS_Date.Year == DateTime.Now.Year
group p by p.PP_ProcedureId into g
select new
{
PP_ProcedureId = g.Key,
ProcCount = g.Count()
}
) on ProcLookup.PL_ProcedureId equals
cyearProc.PP_ProcedureId
orderby cyearProc.ProcCount descending
select new
{
// Columns
PP_ProcedureId = ProcLookup.PP_ProcedureId,
ProcCount = cyearProc.ProcCount
}).ToList();

Related

Join Linq column with minimum value column

I have to join outer table column with inner table minimum value column
Here is my sql query:
SELECT O.Id, O.Name, O.Designation
FROM TableA AS O INNER JOIN
(SELECT MIN(SrNo) AS A_SNo, Id
FROM TableA
WHERE (Active = 1)
GROUP BY Id) AS I ON O.Id = I.Id AND O.SrNo = I.A_SNo AND O.Active = 1
I have tried this:
from tres in TableA join O in
(from tresp in TableA
where tresp.Active == true
group tresp by new { tresp.Id } into G
select new { Id = G.Key.Id, A_Sno =(int?)G.Min(X=>X.SrNo)}
) on new {tres.Id,a=(int?)tres.SrNo } equals new {O.Id,a=O.A_Sno } into tresss
where (tres.Active==true)
select new { tres.Id, tres.Name, tres.Designation }
in sql query I'm not getting duplicate rows but when i tried this in linq getting duplicate rows
try
from tres in TableA join O in
(from tresp in TableA
where tresp.Active == true
group tresp by new { tresp.Id } into G
select new { Id = G.Key.Id, A_Sno =(int?)G.Min(X=>X.SrNo)}
) on new {tres.Id,a=(int?)tres.SrNo } equals new {O.Id,a=O.A_Sno }
where (tres.Active==true)
select new {tres.Id,tres.Name,tres.Designation} into tresss
select new { tresss.Id, tresss.Name, tresss.Designation }

how to write this statement in linq to sql

SELECT TOP (5)
Sales.Product, Sales.Product_Price, COUNT(*) AS CNT,
Products.Category, Products.IMG_URL, Products.Rate_Avg
FROM
Sales
INNER JOIN
Products ON Sales.Product = Products.Product
GROUP BY
Sales.Product, Sales.Product_Price,
Products.Category, Products.IMG_URL, Products.Rate_Avg
HAVING
(COUNT(*) > 1)
ORDER BY CNT DESC
Most of that query has a 1-to-1 correspondence to the equivalent linq-to-sql expression. Though the TOP (5) part needs to be added to the end.
(from s in db.Sales
join p in db.Products on s.Product equals p.Product
group s by new { s.Product, s.Product_Price, p.Category, p.IMG_URL, p.Rate_Avg } into g
where g.Count() > 1
orderby g.Count() descending
select new
{
g.Key.Product,
g.Key.Product_Price,
CNT = g.Count(),
g.Key.Category,
g.Key.IMG_URL,
g.Key.Rate_Avg,
}).Take(5)

How to GroupBy data in Linq to SQL query

I've got a problem in getting my groupby's right in a Linq to SQL query.
I have 3 tables: Customers, Orders and OrderItems. The OrderItems contain the quantity and price of the items purchased.
Now I simply would like to list all the customers with the total price of all orders.
I have (amongst a number of other tries) this, but it's not compiling. There is no TotalPrice item in the Intellisense where I have the ??? in the last line.
var q = (from c in db.Customers
join o in db.Orders on c.ID equals o.Customer
//join oi in db.OrderItems on o.ID equals oi.OrderID
group c by new {c.CustomerName, TotalPrice = o.OrderItems.Sum(x => x.Quantity * x.Price)} into groupby
select groupby);
foreach (var cust in q)
Console.WriteLine("{0} {1}", cust.Min(x => x.CustomerName), cust.Sum(x => x.???);
The (easy, understandable, straight forward and simple) SQL query will look like this:
SELECT C.ID, MIN(CustomerName) CustomerName, SUM(Quantity * Price) OrderPrice
FROM Customers C
INNER JOIN ORDERS O ON C.ID = O.Customer
INNER JOIN OrderItems OI ON O.ID = OI.OrderID
GROUP BY C.ID
This works for me:
This is sums by Customer and Order
var orders = (from c in context.Customers
join o in context.Orders on c.custid equals o.custid
join od in context.OrderDetails on o.orderid equals od.orderid
select new
{
c.custid,
o.orderid,
od.qty,
od.unitprice
}).GroupBy(c => new
{
c.custid,
c.orderid
}).Select(c => new
{
c.Key.custid,
c.Key.orderid,
Summ = c.Sum(d => d.qty * d.unitprice)
}).ToList();
This is sums by Customer only
var orders = (from c in context.Customers
join o in context.Orders on c.custid equals o.custid
join od in context.OrderDetails on o.orderid equals od.orderid
select new
{
c.custid,
od.qty,
od.unitprice
}
).GroupBy(c => new
{
c.custid,
}).Select(c => new
{
c.Key.custid,
Summ = c.Sum(d => d.qty * d.unitprice)
}).ToList();
I can mess with names, but here is LinQ expression with Extension methods syntax that match your SQL:
var q = db.Customers
.GroupBy(x => new
{
x.ID,
x.CustomerName,
}, (x, group) => new
{
Id = x.ID,
CustomerName = x.CustomerName,
TotalPrice = group.Select(y => y.Orders.Sum(z => z.OrderItems.Sum(a => a.Price * a.Quantity)))
});
foreach (var cust in q)
Console.WriteLine("{0} {1}", cust.CustomerName, cust.TotalPrice);
This is also working for me:
var q = (from c in db.Customers
join o in db.Orders on c.ID equals o.Customer
join oi in db.OrderItems on o.ID equals oi.OrderID
group new {c, o.ID, oi.Quantity, oi.Price} by new {c.ID, c.CustomerName} into grp
let TotalPrice = grp.Sum(x => x.Quantity * x.Price)
select new
{
CustomerID = grp.Key.ID,
CustomerName = grp.Key.CustomerName,
TotalPrice
});
and
var q = (from c in db.Customers
join o in db.Orders on c.ID equals o.Customer
join oi in db.OrderItems on o.ID equals oi.OrderID
group new { CustomerID = c.ID, CustomerName = c.CustomerName, Price = oi.Price, Quantity = oi.Quantity} by c.ID into grp
select new
{
ID = grp.Key,
CustomerName = grp.Min(x => x.CustomerName),
TotalPrice = grp.Sum(x => x.Price * x.Quantity)
});

GROUP BY and HAVING in linq

I want to convert this code to linq:
select t1.title, COUNT(*)as num
from t1 INNER join t2 on t2.gId = t1.Id
group by t1.title, t1.cId
having t1.cId = 2
I tried this below code:
from p in db.t1s join r in db.t2s on p.Id equals r.gId
where p.cId == 2
group p by p.title into g
select new{ name = from o in g select o.title, num = g.Count()}
But this doesn't return COUNT correctly.
please guide me how can I solve the problem
thanks
Without sample data its hard to get it right, but try this snippet
from p in db.t1s
join r in db.t2s on p.Id equals r.gId
where p.cId == 2
group p by new {p.title, p.cId} into grouped
select new{ name = grouped.Key.title, num = grouped.Count()}
Also, note that this sql:
select t1.title, COUNT(*)as num
from t1 INNER join t2 on t2.gId = t1.Id
group by t1.title, t1.cId
having t1.cId = 2
Will always return 1 as result of COUNT(*). The reason is that you have filtering t1.cId = 2 and grouping by t1.cId as second parameter.

multiple tables join by Linq

I have 3 tables which named Player, PlayerDetails and Team. I want to write a linq statement such as
from p in Player join d in PlayerDetails on p.ID equals d.PID
and then right join team table, Player has a column named TID which face to Team table's ID.
I have tried to write a statement like
from p in Player join d in PlayerDetails on p.ID equals d.PID into PlayerGroup
from t in team join g in PlayerGroup on t.ID equals g.p.ID
It certainly can't work. I'm not sure how to write such type of query statement, table left join table2 then right join table3.
Who can help?
I believe you could do something like this:
var LeftJoin =
from p in Player
join d in PlayerDetails on p.ID equals d.PID into pd
from d in pd.DefaultIfEmpty()
select new
{
pID = p.ID,
pTID = p.TID,
dID = d.ID
};
var RightJoin =
from t in Team
join l in LeftJoin on t.ID equals l.pTID into tl
from l in tl.DefaultIfEmpty()
select new
{
tID = t.ID,
pID = l.pID,
pTID = l.PTID,
dID = l.dID
};
To do everything in one query, I think you could do (not tested) something like this:
var RightJoin =
from t in Team
join l in
(from p in Player
join d in PlayerDetails on p.ID equals d.PID into pd
from d in pd.DefaultIfEmpty()
select new
{
pID = p.ID,
pTID = p.TID,
dID = d.ID
})
on t.ID equals l.pTID into tl
from l in tl.DefaultIfEmpty()
select new
{
tID = t.ID,
pID = l.pID,
pTID = l.PTID,
dID = l.dID
};

Resources