2010-06-28 4 views
1

У меня есть два словаря в C#.C#: Слияние двух словарей по значениям с использованием LINQ

Два Словари и их calues ​​являются

Dictionary<int,List<string>> D1 = new Dictionary<int,List<string>>(); 
Dictionary<int,List<string>> D2= new Dictionary<int,List<string>>(); 
Dictionary<int,List<string>> D3 new Dictionary<int,List<string>>(); 


D1[1] = new List<string>{"a","b"}; 
D1[2] = new List<string>{"c","d"}; 
D1[3] = new List<string>{"e","f"}; 
D1[4] = new List<string>{"h"}; 

Где 1,2,3 и 4 ключи словаря D1

D2[1] = new List<string>{"a","b"}; 
D2[2] = new List<string>{"c","d"}; 
D2[3] = new List<string>{"e","f"}; 
D2[4] = new List<string>{"g"}; 
D2[5] = new List<string>{"b","h"}; 
D2[6] = new List<string>{"f","l"}; 
D2[7] = new List<string>{"z"}; 

Где 1,2,3,4,5,6 и 7 являются ключами словаря D2

Тогда выходной словарь содержит эти значения,

D3[1] = {"a","b","h"} 
    D3[2] = {"c","d"} 
    D3[3] = {"e","f","l"} 

Примечание: Пожалуйста, возьмите входной словарь со значениями больше, чем 1.Thats почему я устраняющие D1 [4], D2 [4] и D2 [7]

Вот мой код:

  List<int> l_lstTempNets = new List<int>(D1.Keys); 
     int l_nCount = 0; 
     for (int l_nData = 0; l_nData < l_lstTempNets.Count; l_nData++) 
     { 
      D3.Add(l_nCount, D1[l_lstTempNets[l_nData]]); 
      l_nCount++; 
     } 
     l_lstTempNets = new List<int>(D2.Keys); 
     for (int l_nData = 0; l_nData < l_lstTempNets.Count; l_nData++) 
     { 
      D3.Add(l_nCount, D2[l_lstTempNets[l_nData]]); 
      l_nCount++; 
     } 





     List<int> l_lstOuter = new List<int>(D3.Keys); 
     List<int> l_lstInner = new List<int>(D3.Keys); 
     for (int l_nOuter = 0; l_nOuter < l_lstOuter.Count; l_nOuter++) 
     { 
      if (D3.ContainsKey(l_lstOuter[l_nOuter]) == false) 
       continue; 
      List<string> l_lstOuterValue = D3[l_lstOuter[l_nOuter]]; 
      l_lstOuterValue.Sort(); 
      if (l_lstOuterValue.Count == 0 || l_lstOuterValue.Count == 1) 
      { 
       D3.Remove(l_lstOuter[l_nOuter]); 
       continue; 
      } 
      for (int l_nInner = 0; l_nInner < l_lstInner.Count; l_nInner++) 
      { 
       if (l_lstOuter[l_nOuter] != l_lstInner[l_nInner]) 
       { 
        if (D3.ContainsKey(l_lstInner[l_nInner]) == false) 
         continue; 
       List<string> l_lstInnerValue = new List<string>(D3[l_lstInner[l_nInner]]); 
        l_lstInnerValue.Sort(); 
        for (int l_nOuterData = 0; l_nOuterData < l_lstOuterValue.Count; l_nOuterData++) 
        { 
         if (l_lstInnerValue.Contains(l_lstOuterValue[l_nOuterData])) 
         { 
          for (int l_nInnerData = 0; l_nInnerData < l_lstInnerValue.Count; l_nInnerData++) 
          { 
           if (l_lstOuterValue.Contains(l_lstInnerValue[l_nInnerData]) == false) 
           { 
            l_lstOuterValue.Add(l_lstInnerValue[l_nInnerData]); 

           } 
          } 
          IsExists = true; 
          break; 
         } 
         else 
         { 
          IsExists = false; 
         } 
        } 

       } 
       else 
        IsExists = false; 
       if (IsExists) 
       { 
        if (D3.ContainsKey(l_lstInner[l_nInner])) 
         D3.Remove(l_lstInner[l_nInner]); 
       } 
      } 

     } 

можно ли с помощью LINQ Если у вас есть какие-либо вопросы, Plz дайте мне знать

+1

Я не понял правило слияния – Andrey

+1

Я не могу понять, почему здесь используются словари –

+0

Это действительно не совсем понятно, что вы пытаетесь сделать здесь - сначала я думал, что вам нужен объединенный словарь, где каждый Значение было объединением исходных значений, но теперь я думаю, что вы представляете связанный список? Или что-то? – AakashM

ответ

0

из описания вашего запроса, я понял, что вам нужно: 1) Фильтр из любого словаря е ntry с менее чем 2 значениями в списке значений. 2) Сопоставьте записи в D2 и D1, чтобы первый элемент в D2.Value равнялся последнему элементу в D1.Value. 3) Храните в D3 любую запись D1 независимо от соответствия с входами D2. 4) Объедините соответствующие записи, чтобы каждое результирующее значение содержало все элементы из D1.Value и D2.Value.

Кажется, что элементы внутри каждого D1.Value и D2.Value представляют собой некоторую иерархическую систему, где последний элемент в D1.Value ссылается на первый элемент в D2.Value.

Здесь следует мой код:

 var f1 = D1.Where(pair => pair.Value.Count >= 2); 
     var f2 = D2.Where(pair => pair.Value.Count >= 2); 

     var joined = from item1 in f1 
        join item2 in f2 on item1.Value.Last() equals item2.Value.First() into DX 
        from itemX in DX.DefaultIfEmpty() 
        select new { Id = item1.Key, Value1 = item1.Value, Value2 = itemX.Value }; 
     foreach (var item3 in joined) 
     { 
      if (item3.Value2 != null) 
       D3.Add(item3.Id, item3.Value1.Concat(item3.Value2.Skip(1)).ToList()); 
      else 
       D3.Add(item3.Id, item3.Value1.ToList()); 
     } 

f1 и f2 являются аналогами D1 и D2 отфильтрованные содержать только записи с достаточно (2+) элементов. присоединился будет соответствовать всем f1 и f2 на основе объясняются правила и будет производить анонимные элементы, содержащие f1.Key, f1.Value, f2.Value. Последующий цикл добавит к D3 необходимый результат, проверка на f2.Value является null.

С уважением, Daniele.

Смежные вопросы