2011-01-18 33 views
10

Tôi có các đối tượng GroupUser.
đối tượng Group có thuộc tính Users là danh sách Người dùng.
Người dùng có thuộc tính có tên IsEnabled.LINQ to Entities - cách lọc các thực thể con

Tôi muốn viết truy vấn LINQ trả về danh sách Group s, chỉ bao gồm User s có IsEnabled là đúng.

ví dụ như vậy, đối với dữ liệu như dưới đây
AllGroups
nhóm A
User 1 (IsEnabled = true)
User 2 (IsEnabled = true)
tài 3 (IsEnabled = false)

Nhóm B
tài 4 (IsEnabled = true)
tài khoản 5 (IsEnabled = false)
tài 6 (IsEnabled = false)

Tôi muốn nhận
FilteredGroups
nhóm A
User 1 (IsEnabled = true)
User 2 (IsEnabled = true)

Nhóm B
Người dùng 4 (IsEnabled = true)

Tôi đã thử các truy vấn sau đây, nhưng Visual Studio nói với tôi rằng
[tài sản hoặc indexer 'Người dùng' không thể được gán cho - đó là chỉ đọc]

FilteredGroups = AllGroups.Select(g => new Group() 
        { 
         ID = g.ID, 
         Name = g.Name, 
         ... 
         Users = g.Users.Where(u => u.IsInactive == false) 
        }); 

cảm ơn bạn đã giúp đỡ của bạn!

+0

bạn đang sử dụng EF4? Nếu vậy, bạn có đang sử dụng POCO không? 'Group.Users' được khai báo như thế nào? – RPM1984

+2

Bạn có thể dễ dàng thực hiện điều này với Bộ lọc được bao gồm. Bình chọn cho tính năng [ở đây] (https://entityframework.codeplex.com/workitem/47)! – Chris

Trả lời

8

tôi quản lý để thực hiện điều này bằng cách chuyển các truy vấn ngược:

var users = (from user in Users.Include("Group") 
      where user.IsEnabled 
      select user).ToList().AsQueryable() 

from (user in users 
     select user.Group).Distinct() 

Bằng việc sử dụng ToList(), bạn buộc một khứ hồi cơ sở dữ liệu đó là cần thiết bởi vì nếu không thực hiện chậm đi theo cách này. Truy vấn thứ hai chỉ tái sắp xếp lại dữ liệu đã truy xuất.

Lưu ý: Bạn có thể không thể udpate các thực thể của bạn sau đó!

+0

bạn có thể giúp tôi với truy vấn LINQ này không: http: //stackoverflow.com/questions/38120664/how-to-group-by-on-2-child-entities-and-get-total-of-both-this- các thực thể con –

9

Không có "đẹp" cách để làm điều này, nhưng bạn có thể thử này - dự án cả hai, Group và lọc Users vào một đối tượng ẩn danh, và sau đó Select chỉ Groups:

var resultObjectList = AllGroups. 
         Select(g => new 
           { 
            GroupItem = g, 
            UserItems = g.Users.Where(u => !u.IsInactive) 
           }).ToList(); 

FilteredGroups = resultObjectList.Select(i => i.GroupItem).ToList(); 

isn này' t một tính năng được ghi lại và phải làm theo cách EF xây dựng các truy vấn SQL - trong trường hợp này nó sẽ lọc ra bộ sưu tập con, vì vậy danh sách FilteredGroups của bạn sẽ chỉ chứa những người dùng đang hoạt động.

Nếu công trình này, bạn có thể thử kết hợp các mã:

FilteredGroups = AllGroups. 
       Select(g => new 
           { 
            GroupItem = g, 
            UserItems = g.Users.Where(u => !u.IsInactive) 
           }). 
       Select(r => r.GroupItem). 
       ToList(); 

(Đây là chưa được kiểm tra và kết quả phụ thuộc vào cách EF sẽ xử lý thứ hai Select, vì vậy nó sẽ được tốt đẹp nếu bạn cho chúng tôi biết phương thức hoạt động sau khi bạn đã thử).

1

thử một cái gì đó như thế này và bạn vẫn sẽ có các đơn vị của bạn:

FilteredGroups = AllGroups.Select(g => new 
{ 
    Group = g, 
    Users = g.Users.Where(u => u.IsInactive == false) 
}).AsEnumerable().Select(i => i.Group); 

Bằng cách đó bạn vẫn có thể sử dụng Group.Users

0

Nếu bạn muốn giữ lại cấu trúc tổ chức của bạn, hãy thử này :

var userGroups = context.Users.Where(u => !u.IsInactive).GroupBy(u => u.Group); 

foreach (var userGroup in userGroups) 
{ 
    // Do group stuff, e.g.: 
    foreach (var user in userGroup) 
    { 
    } 
} 

Và bạn chắc chắn có thể sửa đổi các thực thể của mình!

Các vấn đề liên quan