[英]LINQ Left Join And Right Join
我需要幫助,
我有兩個名為 A 和 B 的數據表,我需要 A 中的所有行和 B 的匹配行
前任:
A: B:
User | age| Data ID | age|Growth
1 |2 |43.5 1 |2 |46.5
2 |3 |44.5 1 |5 |49.5
3 |4 |45.6 1 |6 |48.5
我需要輸出:
User | age| Data |Growth
------------------------
1 |2 |43.5 |46.5
2 |3 |44.5 |
3 |4 |45.6 |
您提供的示例數據和輸出並未演示左連接。 如果是左連接,您的輸出將如下所示(注意我們如何為用戶 1 獲得 3 個結果,即用戶 1 擁有的每條增長記錄一次):
User | age| Data |Growth
------------------------
1 |2 |43.5 |46.5
1 |2 |43.5 |49.5
1 |2 |43.5 |48.5
2 |3 |44.5 |
3 |4 |45.6 |
假設您仍然需要左連接; 以下是在 Linq 中執行左連接的方法:
var results = from data in userData
join growth in userGrowth
on data.User equals growth.User into joined
from j in joined.DefaultIfEmpty()
select new
{
UserData = data,
UserGrowth = j
};
如果您想進行正確的連接,只需交換您從中選擇的表,如下所示:
var results = from growth in userGrowth
join data in userData
on growth.User equals data.User into joined
from j in joined.DefaultIfEmpty()
select new
{
UserData = j,
UserGrowth = growth
};
代碼的重要部分是 into 語句,然后是DefaultIfEmpty 。 這告訴 Linq,如果另一個表中沒有匹配結果,我們希望使用默認值(即 null)。
瓊斯醫生展示了左外連接,但正確答案會略有不同 - 因為在原始問題中,兩個表在年齡字段上鏈接,因此應使用以下代碼來完全根據需要獲得結果。
....
//ctx = dataContext class - not shown here.
var user1 = new UserData() { User = 1, Age = 2, Data = 43.5 };
var user2 = new UserData() { User = 2, Age = 3, Data = 44.5 };
var user3 = new UserData() { User = 3, Age = 4, Data = 45.6 };
ctx.UserData.AddRange(new List<UserData> { user1, user2, user3 });
var growth1 = new UserGrowth() { Id = 1, Age = 2, Growth = 46.5 };
var growth2 = new UserGrowth() { Id = 1, Age = 5, Growth = 49.5 };
var growth3 = new UserGrowth() { Id = 1, Age = 6, Growth = 48.5 };
ctx.UserGrowth.AddRange(new List<UserGrowth> { growth1, growth2, growth3 });
var query = from userData in ctx.UserData
join userGrowth in ctx.UserGrowth on userData.Age equals userGrowth.Age
into joinGroup
from gr in joinGroup.DefaultIfEmpty()
select new
{
User = userData.User,
age = userData.Age,
Data = (double?)userData.Data,
Growth = (double?)gr.Growth
};
Console.WriteLine("{0} | {1} | {2} | {3}", "User", "age", "Data", "Growth");
foreach (var x in query)
{
Console.WriteLine("{0} | {1} | {2} | {3}", x.User, x.age, x.Data, x.Growth);
}
.... with following entity classes:
public class UserData
{
[Key]
public int User { get; set; }
public int Age { get; set; }
public double Data { get; set; }
}
public class UserGrowth
{
public int Id { get; set; }
public int Age { get; set; }
public double Growth { get; set; }
}
簡單的方法是使用 Let 關鍵字。 這對我有用。
from AItem in Db.A
Let BItem = Db.B.FirstOrDefault(x => x.id == AItem.id )
Where SomeCondition
Select new YourViewModel
{
X1 = AItem.a,
X2 = AItem.b,
X3 = BItem.c
}
這是Left Join的模擬。 如果 B 表中的每個項目都與 A 項目不匹配,則 BItem 返回 null
簡單示例
模型
class Employee
{
public string Name { get; set; }
public int ID { get; set; }
public int ProjectID { get; set; }
}
class Project
{
public int ProjectID { get; set; }
public string ProjectName { get; set; }
}
方法
public void leftrighjoin(){
Project P1 = new Project() { ProjectID = 1, ProjectName = "UID" };
Project P2 = new Project() { ProjectID = 2, ProjectName = "RBS" };
Project P3 = new Project() { ProjectID = 3, ProjectName = "XYZ" };
// Employee List
List<Employee> ListOfEmployees = new List<Employee>();
ListOfEmployees.AddRange((new Employee[]
{
new Employee() { ID = 1, Name = "Sunil", ProjectID = 1 },
new Employee() { ID = 1, Name = "Anil", ProjectID = 1 },
new Employee() { ID = 1, Name = "Suman", ProjectID = 2 },
new Employee() { ID = 1, Name = "Ajay", ProjectID = 3 },
new Employee() { ID = 1, Name = "Jimmy", ProjectID = 4 }}));
//Project List
List<Project> ListOfProject = new List<Project>();
ListOfProject.AddRange(new Project[] { P1, P2, P3 });
//Left join
var Ljoin = from emp in ListOfEmployees
join proj in ListOfProject
on emp.ProjectID equals proj.ProjectID into JoinedEmpDept
from proj in JoinedEmpDept.DefaultIfEmpty()
select new
{
EmployeeName = emp.Name,
ProjectName = proj != null ? proj.ProjectName : null
};
//Right outer join
var RJoin = from proj in ListOfProject
join employee in ListOfEmployees
on proj.ProjectID equals employee.ProjectID into joinDeptEmp
from employee in joinDeptEmp.DefaultIfEmpty()
select new
{
EmployeeName = employee != null ? employee.Name : null,
ProjectName = proj.ProjectName
};
//Printing result of left join
Console.WriteLine(string.Join("\n", Ljoin.Select(emp => " Employee Name = " +
emp.EmployeeName + ", Project Name = " + emp.ProjectName).ToArray<string>()));
//printing result of right outer join
Console.WriteLine(string.Join("\n", RJoin.Select(emp => " Employee Name = " +
emp.EmployeeName + ", Project Name = " + emp.ProjectName).ToArray<string>()));
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.