2013-01-11 65 views
5

Tôi có hai bảng, mỗi mô hình riêng của họ ...Matching hai Danh sách các loại khác nhau với nhau

class FamilyMan 
    { 
     public int family_ID {get; set;} 

     public string name {get; set;} 
     public string fav_color {get; set;} 
    } 

    class BusinessMan 
    { 
     public int work_ID {get; set;} 

     public string name {get; set;} 
     public string fav_color {get; set;} 

     //unrelated data etc 
     public string job_title {get; set;} 
    } 

... và tôi muốn để có thể phù hợp với tất cả FamilyMans đến BusinessMans phù hợp dựa trên namefav_color.

Tôi hiện đang có một cái gì đó như:

//fill lists from database 
    var family_list = dbContext.FamilyMen.ToList(); 
    var busy_list = dbContext.BusinessMen.ToList(); 
    //create empty dict for matching the two types 
    var matches = new Dict<FamilyMan, BusinessMan>(); 


    foreach (FamilyMan fam_man in family_list) { 
     foreach (BusinessMan busy_man in busy_list) { 
      //if both names and colors match, consider them a matching 
      //object and add them each to the dict 
      if (fam_man.name == busy_man.name && 
        fam_man.color == busy_man.color) { 
       matches_MtO[fam_man] = busy_man; 
      } 
     } 
    } 

nhưng phải mất khá thời gian để hoàn thành.

Tôi cũng đã xem xét vòng lặp trên một danh sách có foreach và sau đó sử dụng LINQs FirstOrDefault để khớp với chúng, nhưng hiệu quả có vẻ giống nhau.

Có cách nào tốt hơn để đi về kết hợp FamilyMan s và BusinessMan s với nhau không?

Trả lời

3

Bạn nên sử dụng tham gia cú pháp LINQ của. Điều này sẽ cho phép cơ sở dữ liệu phụ trợ thực hiện việc so khớp và chỉ trả lại kết quả.

Để kích hoạt một tham gia vào một phím composite, làm theo các MSDN guidance here.

var query = from fm in dbContext.FamilyMen 
      join bm in dbContext.BusinessMen on 
       new { bm.name, bm.color } equals new { fm.name, fm.color } 
      select new { 
       FamilyMan = fm, 
       BusinessMan = bm 
      }; 

var resultList = query.ToList(); 
+0

Tôi phải thêm các tên trùng khớp vào hai đối tượng ẩn danh đầu tiên,' Name' và 'Color', tương ứng, và nó dường như hoạt động ngay lập tức. Điều này hoạt động thực sự tốt, tôi sẽ chỉ cung cấp cho @Gerve một phút để khắc phục truy vấn của anh ấy để giải quyết vấn đề 'Expression Expected' nếu có thể, nếu không tôi sẽ chấp nhận câu trả lời này. Cảm ơn! – TankorSmash

+0

"tên phù hợp" là một cái gì đó như 'new {Name = bm.name, Color = bm.color}' cho cả hai đối tượng. Từ các tài liệu bạn đã liên kết: 'Ví dụ, nếu bảng Đơn hàng và bảng OrderDetails từng sử dụng các tên khác nhau cho cột của chúng, bạn có thể tạo các khóa tổng hợp bằng cách gán tên giống nhau trong các loại ẩn danh:' Cảm ơn một lần nữa! – TankorSmash

2

Vòng lặp của bạn thông qua cả hai danh sách, là O (N-bình phương).

Khi một mục được khớp, nó không cần phải khớp lại. Bạn có thể xóa các mục phù hợp khỏi danh sách, giảm các so sánh không cần thiết.

Tốt hơn, vì bạn đang khớp trên hai thuộc tính giống hệt nhau, bạn có thể tạo từ điển bằng cách sử dụng hàm băm đại diện cho thuộc tính được kết hợp làm khóa. Sau đó, bạn có thể lặp qua các khóa của family_list_dictionary và chỉ cần tìm một khóa phù hợp trong busy_list_dictionary.

+0

Tôi chưa bao giờ làm việc với băm trước đó, bạn có bất kỳ ví dụ tốt ngay? Tôi sẽ lặp qua cả hai bảng, kéo hai thuộc tính, chuyển đổi chúng thành một băm bằng cách nào đó, lưu băm vào danh sách, sau đó đi qua danh sách băm và so sánh băm gia đình với băm kinh doanh? – TankorSmash

+0

Tôi hiện không có máy tính. Tôi có thể cung cấp cho bạn một ví dụ chi tiết trong vài giờ. –

+0

Đừng lo lắng về nó, nếu bạn không muốn, tôi tìm thấy một câu trả lời làm việc http://stackoverflow.com/a/14283717/541208. Tôi muốn học cách làm như thế, nhưng không phải lo lắng. – TankorSmash

4

có một truy vấn LINQ như thế này là nhanh hơn:

var matches = (
    from f in family_list 
    join b in busy_list 
    on f.color == b.color 
    && f.name == b.name 
    select new {f, b} 
); 
+0

sau '... == b.color' '&&' dường như không hoạt động. 'Expression Expected' – TankorSmash

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