2013-01-17 115 views
0

我有2個表格,我需要從...房間和地址。 Rooms表中有一個AddressID字段,但它可以爲空,所以關係爲0到1.我一直在試圖編寫一個LINQ語句,它將返回一個特定的房間和地址信息(如果存在)。我的模型定義爲這樣:LINQ - 左外連接 - 更好的方法

public partial class Room 
{ 
    public Room() 
    { 
     this.Address = new HashSet<Address>(); 
    } 

    public int RoomID { get; set; } 
    public Nullable<int> AddressID { get; set; } 
    public string Comments { get; set; } 
    public string Notes { get; set; } 

    public virtual ICollection<Address> Address { get; set; } 
} 

我試圖在LINQ語句中使用在.include(「地址」),但它沒有工作,我相信它是由加入語句(我讀引起的,一旦它被使用,它會默默地放棄包含)。

這裏的周圍有一個醜陋的方式,但我知道有一個更好的辦法:

var csdDB = new CSDContext(CustomerCode); 

IList<Room> rooms = (from r in csdDB.Rooms 
         join sr in csdDB.SiteRooms 
          on r.RoomID equals sr.RoomID 
         where sr.SiteID == id 
         orderby r.RoomName 
         select r).ToList<Room>(); 

int? addressID = rooms.FirstOrDefault<Room>().AddressID; 

if (addressID != null) 
{ 
    IList<Address> address = (from a in csdDB.Addresses 
           where a.AddressID == addressID 
           select a).ToList<Address>(); 

    rooms.FirstOrDefault<Room>().Address = address; 
} 

我試圖直接做過濾的結果:

IList<Address> address = (from a in csdDB.Addresses 
          where a.AddressID == rooms.FirstOrDefault().AddressID 
          select a).ToList<Address>(); 

但它拋出一個錯誤:

Unable to create a constant value of type 'Models.CSD.Room'. Only primitive types or enumeration types are supported in this context. 

有關如何使這個更清潔/更好的任何建議表示讚賞!

+0

你說'Room'有0-1與'Address'關係,那麼爲什麼'Room'有'ICollection的

'? –

+0

對不起......這是我們正在尋求擴展....這意味着,最終,允許客房有0到很多地址。 – Robert

+0

然後你不需要'可空的 AddressID'。我認爲這令人困惑。地址表應該有一個'RoomID'來代替。 –

回答

0

合併左加入LINQ可能是這個樣子:

var results = (from r in csdDB.Rooms 
       join sr in csdDB.SiteRooms 
        on r.RoomID equals sr.RoomID && sr.SiteID equals id 
       join addr in csdDB.Addresses 
        on r.AddressID equals addr.AddressID into roomAddrs 
       from roomAddr in roomAddrs.DefaultIfEmpty(new Address()) 
       select new 
       { 
        Room = r, 
        Address = roomAddr 
       }