-1

私は、OldCustomers、NewCustomers という 2 つの List インスタンスを持っています。

List<Customer> OldCustomers;

List<Customer> NewCustomers;

Oldcustomers と NewCustomers の両方のユニオンが欲しいだけです。つまり、CustomerID 100 が OldCustomerList と NewCustomer リストに存在する場合、OldCustomer リストの顧客の詳細を削除し、NewCustomer リストを結果リストに配置する必要があります。

List<Customer> NewCustomers;
    Union
List<Customer> OldCustomers;

LINQでそれを行うにはどうすればよいですか?

前もって感謝します、

4

6 に答える 6

1

を使用するにはUnion、次のようにカスタマイズする必要がありますEqualityComparer

public class CusComparer : EqualityComparer<Customer>
{
    public override bool Equals(Customer x, Customer y)
    {
        return x.CustomerID == y.CustomerID;
    }

    public override int GetHashCode(Customer obj)
    {
        return obj.CustomerId.GetHashCode();
    }
}

それで:

var unionCustomers = NewCustomers.Union(OldCustomers, new CusComparer());
于 2012-10-10T06:47:14.177 に答える
0

UnionCustomer オブジェクトのインスタンスを比較します (IEqualityComparer使用されていない場合)。あなたは次のようなものを探していると思いますUnionBy

var finalList = NewCustomers.Concat(OldCustomers)
                    .GroupBy(x => x.CustomerID)
                    .Select(x => x.First())
                    .ToList();

- 編集 -

可能なUnionBy実装:

var finalList = NewCustomers.UnionBy(OldCustomers, c => c.CustomerID).ToList();

-

public static class SOExtension
{

    public static IEnumerable<T> UnionBy<T,V>(this IEnumerable<T> list, IEnumerable<T> otherList,Func<T,V> selector)
    {
        HashSet<V> set = new HashSet<V>();

        foreach (T t in list)
        {
            set.Add(selector(t));
            yield return t;
        }
        foreach(T t in otherList)
        {
            if(!set.Contains(selector(t)))
                yield return t;
        }
    }
}
于 2012-10-10T06:46:06.270 に答える
0
HashSet<Customer> set = new HashSet<Customer>(list1);
set.SymmectricExceptWith(list2); // Or other userful methods.
于 2012-10-10T07:16:49.940 に答える
0

このようなユニオン関数を使用できます

sequence1.Union(sequence2)

すなわち

var custlist =  NewCustomers.Union(OldCustomers).ToList(); 

Read : Enumerable.Union メソッド (IEnumerable、IEnumerable)

例 :

            int[] ints1 = { 5, 3, 9, 7, 5, 9, 3, 7 };
            int[] ints2 = { 8, 3, 6, 4, 4, 9, 1, 0 };

            IEnumerable<int> union = ints1.Union(ints2);

            foreach (int num in union)
            {
                Console.Write("{0} ", num);
            }

            /*
             This code produces the following output:

             5 3 9 7 8 6 4 1 0
            */
于 2012-10-10T06:36:40.003 に答える
0

Unionのように使用できます

var union = NewCustomers.Union(OldCustomers);

おそらく、クラスに独自の比較子を実装する必要がありますCustomer

于 2012-10-10T06:37:57.293 に答える
0

したがって、すべての新規顧客と、新しいリストに含まれていないすべての古い顧客を取得する必要があります。

List<Customer> customers = NewCustomers.Concat(OldCustomers.Except(NewCustomers)).ToList();

IEqualityComparer<T>顧客を比較するための一般的なインターフェースを実装することを忘れないでください (おそらく によってCustomerID)。GetHashCodeしたがって、独自のおよびEqualsメソッドを提供する必要がありますCustomer

可能な実装は次のとおりです。

public class Customer 
{
    public int CustomerID { get; set; }
    public string CustomerName { get; set; }

    public override bool Equals(Object obj)
    {
        Customer cust = obj as Customer;
        if (cust == null) return false;
        return cust.CustomerID == CustomerID;
    }

    public override int GetHashCode()
    {
        return CustomerID.GetHashCode();
    }

    public class Comparer : IEqualityComparer<Customer>
    {
        public bool Equals(Customer x, Customer y)
        {
            if (x == null && y == null) return true;
            if (x == null || y == null) return false;
            return x.Equals(y);
        }

        public int GetHashCode(Customer obj)
        {
            if (obj == null) return -1;
            return obj.GetHashCode();
        }
    }
}

EqualsGetHashCodeをオーバーライドすることに注意してくださいCustomerIEqualityComparer<Customer>この方法では、 to Except(または比較子を渡すことができる他のメソッド)のインスタンスを渡す必要さえありません。

しかし、完全を期すためにComparer、インターフェイスを実装するクラスも追加したので、Except に渡すこともできます。

NewCustomers.Concat(OldCustomers.Except(NewCustomers, new Customer.Comparer()));
于 2012-10-10T06:58:24.153 に答える