Linq. How to query list within list?

10,387

Solution 1

Flatten the list of list of addresses by projecting each store to its list of addresses, use SelectMany to achieve the flattening, and then take only those where the address type is physical:

var addressesToModify = 
    storeList.SelectMany(store => store.AssetAddresses)
             .Where(address => address.AddressType.Name == "PHYSICAL");

In query syntax:

var addressesToModify =
    from store in storeList
    from address in store.AssetAddresses
    where address.AddressType.Name == "PHYSICAL"
    select address;

Notice how it reads exactly like we described. From each store in the storeList, from each address in store.AssetAddresses where address is a physical address, select address.

Now iterate the results of the query and modify as needed.

Also, I strongly suggest making an enum

public enum AddressType { Physical, Alternative, Mailing }

and changing Address.AddressType to be of this type

public AddressType AddressType { get; }

and then you can write

where address.AddressType == AddressType.Physical

or

.Where(address => address.AddressType == AddressType.Physical);

Solution 2

You need to use SelectMany to flattern out the list of addresses.

var result =
  storeList
  .SelectMany(store => store.AssetAddress)
  .Where(address => address.AddressType == "PHYSICAL")
  .FirstOrDefault();

I'm guessing there will also be a where on the storeList so that you only get the address of the store you're interested in.

Share:
10,387
bobetko
Author by

bobetko

Updated on June 13, 2022

Comments

  • bobetko
    bobetko almost 2 years

    I have Store List (storeList) object. (Consists of list of Stores) Each Store has list of Addresses. Each address have AddressType property that can be PHYSICAL, ALTERNATIVE or MAILING.

    I am trying to return PHYSICAL Address object so I can modify its properties:

    This is my first attempt:

    StoreAddressList result = 
        (from str in storeList
         where
         str.AssetAddresses.Any(p => p.AddressType.Name == "PHYSICAL")
         select str.AssetAddresses).FirstOrDefault();
    

    As a result I expect to get list with only one item (where address type is PHYSICAL), but I get list with 3 items (with all three types). What's wrong here?

    Thanks

  • bobetko
    bobetko over 12 years
    :-). You are fast. Thanks a lot.