I have two generic lists of type T. Both lists contain same type, and I'd like to create a third list (or a filtered version of list 2) based on the items in list two that do not exist in List 1, based on the ID of each item.

Each list holds a "Package" object, which has an ID property.

Right now I mocked up the code using For Each loops, which I know is horrible (the Big O is constant time) so I'd like a more efficent method. 

this code is in VB per project requirments, but I prefer C# - so either code sample would work for me.

```
Private Sub RemoveStockPackagesFromSelection()

    Dim p As Package
    Dim packageList As List(Of Package) = New List(Of Package)
    Dim stockPackageList As List(Of Package) = New List(Of Package)
    Dim result As List(Of Package) = New List(Of Package)

    ' Fill list with User's Packages
    For i As Integer = 0 To ListBox2.Items.Count - 1
        p = New Package
        p.Id = CInt(ListBox2.Items(i).Value)
        p.Name = ListBox2.Items(i).Text
        packageList.Add(p)
    Next

    ' Fill list with Stock Packages to compare:
    Dim ds As DataSet = DAL.GetStandardPackages()

    For Each dr As DataRow In ds.Tables(0).Rows
        p = New Package
        p.Id = CInt(dr.Item("id"))
        stockPackageList.Add(p)
    Next

    ' Do Compare and Filter
    For Each p1 As Package In packageList
        For Each p2 As Package In stockPackageList
            If Not p1.Id = p2.Id Then
                result.Add(p2)
            End If
        Next
    Next

    ' Here is our new trimmed list:
    Response.Write(result.Count)

End Sub

```

What is a nice and clean LINQ or Lamda way of doing this filtering? What is the Big O of my method and what would be the Big O of the proposed method (just to satify my curiosity).

Thanks