简体   繁体   English

过滤对象列表

[英]Filter a list of objects

I have a list of objects in an ArrayList PList . 我在ArrayList PList有一个对象列表。 The object looks like this 对象看起来像这样

Product 
{
    int ProductId,
    string ProductDescription,
    int StoreId 
    int supplierid
}

I would like to add non repeating combination of Products into another array 我想将非重复的产品组合添加到另一个数组中

Product[] Parray

example: 例:

ArrayList Plist has : ArrayList Plist具有:

productid , productdescription, storeid, supplierid

1, "AB", 11 , 123
2, "CD", 24 ,454
1, "AB", 11 ,431

I would like the Product[] Parray to have 我希望Product[] Parray

productid , productdescription, storeid, supplierid
1, "AB", 11 ,123
2, "CD", 24 , 454

I know that I can use a hashtable for key value pairs ,but in this case I have 3 keys ProductId, description & storeid 我知道我可以将散列表用于键值对,但是在这种情况下,我有3个键ProductId,description和storeid

Here is my code as of now: 到目前为止,这是我的代码:

private Types.Product[] LoadProducts()
{
    ArrayList PList = new ArrayList(); 
    // Business Logic , extracting values from xml using xpath
    //Loop though each xml node
    for (int j = 0; j < xmlprodlist.Count; j++)
    {
        //Business logic
        PList.Add(call another function here);
    }
    //What code here ??
    Types.Product[] PArray = (Types.Product[])PArrayList.ToArray(typeof(Types.Product));   
    return PArray;
}

Can anyone tell me what code I need to add above in the place what code here ? 谁能告诉我我需要在此处添加哪些代码的地方?

You could use a simple GroupBy to group your data, and select the first item of each group: 您可以使用简单的GroupBy对数据进行分组,然后选择每个组的第一项:

Product[] Parray = PList.OfType<Product>()
                        .GroupBy(p => new {p.ProductId, p.ProductDescription, p.StoreId})
                        .Select(p => p.First())
                        .ToArray();

Note that you don't have a reason to use ArrayList anymore (you even tagged your question C# 4.0), better use the generic List<T> class, which will make your code more typesafe and more understandable. 请注意,您不再有理由使用ArrayList (甚至标记了C#4.0问题),最好使用通用的List<T>类,这将使您的代码更加类型安全且更易于理解。

Another way is to provide a IEqualityComparer that compares the three properties in question to the Distinct method: 另一种方法是提供IEqualityComparer ,以将所讨论的三个属性与Distinct方法进行比较:

Product[] Parray = PList.OfType<Product>()
                        .Distinct(theIEqualityComparer)
                        .ToArray();

I probably did not understand... why not an hastable int->Product (productId->Product) 我可能不明白...为什么不使用hastable int-> Product(productId-> Product)

something like (sorry I don't have ac# compiler here, this is just a draft) 像这样(对不起,我这里没有ac#编译器,这只是草稿)

proDictionary<int, Product> table = new Dictionary<int, Product>();

foreach (var x : inproducts)
     // if (!table.Keys.Contains(x)) // if you want to keep the first
    table.Add(x.ProductId, x);

return table.Values.ToArray();

From what i understand you have a list of products and you want a distict list based on the ID. 据我了解,您有一个产品列表,并且您想要基于ID的差异列表。 First override Equals and GetHashCode in the Product class and then use LINQ to get the distict items: 首先在Product类中重写Equals和GetHashCode,然后使用LINQ获取离散项:

public class Product
{
    public int ProductId;
    public string ProductDescription;
    public int StoreId;
    public int supplierid;


    public override bool Equals(object obj)
    {
        if (obj == null || GetType() != obj.GetType())
            return false;

        return ProductId == ((Product)obj).ProductId;
    }


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

And use it like this 像这样使用

List<Product> products = new List<Product>();
products.Add(new Product() { ProductId = 1, ProductDescription = "Product 1" });
products.Add(new Product() { ProductId = 2, ProductDescription = "Product 2" });
products.Add(new Product() { ProductId = 3, ProductDescription = "Product 3" });
products.Add(new Product() { ProductId = 1, ProductDescription = "Product 1 again" });

var distictItems = products.Distinct().ToList();
Console.WriteLine(distictItems.Count()); //This prints 3

One way to do this would be to write an implementation of IEqualityComparer. 一种实现方法是编写IEqualityComparer的实现。 Something like: 就像是:

public class ProductEqualityComparer : IEqualityComparer<Product>
{
    public bool Equals(Product x, Product y)
    {
        return x != null && y != null &&
               x.ProductId == y.ProductId &&
               x.ProductDescription == y.ProductDescription &&
               x.StoreId == y.StoreId;
    }

    public int GetHashCode(Product obj)
    {
        return String.Format("{0}-{1}-{2}",
            obj.ProductId,
            obj.ProductDescription,
            obj.StoreId)
            .GetHashCode();
    }
}

You could then do: 然后,您可以执行以下操作:

var comparer = new ProductEqualityComparer();
var array = (Types.Product[])PList.ToArray(typeof(Types.Product));
var distinct = array.Distinct(comparer);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM