2010-07-23 3 views
0

Мое пересечение в LINQ каким-то образом не работает. У меня есть два листа Excel. Я получаю его с помощью LinQToExcel и (LinQToExcel не поддерживает выступление VisitSubQuery. Мне нужно сделать дополнительную работу). КоличествоДанные Excel с использованием LinQ Пересечение

List<BoardSheet> sourceTest = (from t in Boards[0] 
         where t["Board"] == boardName 
         select new CircuitSet 
          { 
           ID = string.Format(t["ID"]), 
           Data = string.Format(t["Data"]), 
           CtrlType = string.Format(t["CtrlType"]), 
           sys = string.Format(t["sys"]), 
           code = string.Format(t["code"]) 
          } 
         ).ToList<BoardSheet>(); 

      List<BoardSheet> targetTest = (from t in Boards[0] 
              where t["Board"] == boardName 
              select new CircuitSet 
              { 
               ID = string.Format(t["ID"]), 
               Data = string.Format(t["Data"]), 
               CtrlType = string.Format(t["CtrlType"]), 
               sys = string.Format(t["sys"]), 
               code = string.Format(t["code"]) 
              } 
         ).ToList<BoardSheet>(); 

      IEnumerable<BoardSheet> board = sourceTest.Intersect(targetTest); 

платы всегда возвращает 0. Но когда я итерацию беспересадочного значения полого sourceTest и targetSet я вижу общие значения полей.

+0

вы пробовали реализации пользовательского IEqualityComparer ? – Francisco

+0

Нет Francisco.I думал, что единственный способ найти общий набор строк - это использовать «Пересечение». – Webbies

+0

Существует несколько строк, общих как между источником, так и с целью. Я проверил его, записав значения отдельного списка исходных и целевых плат отдельно. – Webbies

ответ

0

Это примеры ссылочных типов. Intersect использует DefaultComparer для ссылочных типов, который является ReferenceEquals. Поскольку sourceTest не имеет общих экземпляров с targetTest, результаты не найдены.

Вы можете создать компаратор, или вы могли бы присоединиться, как это:

List<CircuitSet> results = 
(
    from s in sourceTest 
    join t in targetTest 
    on s.Id equals t.Id 
    where s.Data == t.Data && s.ControlType == t.ControlType ... 
    select s 
).ToList(); 
+0

Спасибо, Дэвид, ваш код работал. – Webbies

0

Я думаю, что простым способом было бы реализовать IEqualityComparer<CircuitSet>. Если ключ CircuitSet является ID, то вы могли бы сделать это следующим образом:

public class CircuitSetComparer : IEqualityComparer<CircuitSet> 
{ 

    #region IEqualityComparer<CircuitSet> Members 

    public bool Equals(CircuitSet x, CircuitSet y) 
    { 
     return x.ID == y.ID; 
    } 

    public int GetHashCode(CircuitSet obj) 
    { 
     return obj.ID;    
    } 

    #endregion 
} 

Затем в коде:

IEnumerable<BoardSheet> board = sourceTest.Intersect(targetTest, new CircuitSetComparer()); 

метод GetHashCode сложно, хотя, но это должно быть хорошо, если мои предположения (ID существо ключ) являются правильными.

+0

Спасибо, Francisco, я попробую и опубликую результат, если он сработает или нет. – Webbies

0

, но я изменил запрос на основе того, что Дэвид предложил

List<BoardSheet> sourceTest =(from s in (from t in Boards[0] 
             where t["Board"] == boardName 
             select new CircuitSet 
             { 
              ID = string.Format(t["ID"]), 
              Data = string.Format(t["Data"]), 
              CtrlType = string.Format(t["CtrlType"]), 
              sys = string.Format(t["sys"]), 
              code = string.Format(t["code"]) 
             } 
         ).ToList<BoardSheet>() jon tbl in (from t in Boards[0] 
             where t["Board"] == boardName 
             select new CircuitSet 
             { 
              ID = string.Format(t["ID"]), 
              Data = string.Format(t["Data"]), 
              CtrlType = string.Format(t["CtrlType"]), 
              sys = string.Format(t["sys"]), 
              code = string.Format(t["code"]) 
             } 
        ).ToList<BoardSheet>() on s.ID equals tbl.ID select s).ToList<BoardSheet>() ; 
Смежные вопросы