1

I have two custom classes in VB.NET and I am using them as lists of classes to contain multiple elements with these properties

One is called materialsDefinition which contains the following:

Public Property id As Integer
Public Property name As String

Public Sub New(ByVal identification As Integer, ByVal material As String)
    id = identification
    name = material
End Sub

A list of this class will be used as a materials dictionary, where you will have an ID, for example "1", and a material name, "A_286", or for example "2" and "17-4PH"

{"1", "A_286"}, {"2", "17-4PH"}

Another class is componentInfo, with a similar structure to the other class:

Public Property componentName As String
Public Property materialID As Integer

Public Sub New(ByVal component As String, ByVal identification As Integer)
    materialID = identification
    componentName = component
End Sub

Where you will have a name of the component in an assembly, for example "Pin" and its material ID "1", which corresponds to the material in the other class, A_286, and "Nut" and its material ID "2" corresponding to 17-4PH

{"Pin", "1"}, {"Nut", "2"}

I want to create a function that looks up and matches the material ID that exists in both classes, and saves the material name in a new array that will contain the following information:

{"Pin", "A_286"}, {"Nut", "17-4PH"}

I'm not sure how though, I thought the most rudimentary solution first which will be looking one by one in a If loop inside a for loop but it would be better to use a "Find" function.

The issue I have is I don't know how to use a find function, or findIndex, or Exists in VB.NET and in a list of a custom class.

Also the size of both lists can be different and the materials list be bigger, or shorter than the component list.

I would appreciate any input given. Thanks.

1

1 Answer 1

1
Function MatchParts(materials As IEnumerable(Of materialsDefinition), components As IEnumerable(Of componentInfo) As IEnumerable(Of (String, String))
    Return materials.Join(components, 
         Function(m) m.id,
         Function(c) c.materialID ,
         Function(m, c) (c.componentName, m.name) )
End Function

It's annoying to me we don't have .Join() overloads like this:

Function Join(Of TOuter, TInner, TResult)(outer As IEnumerable(Of TOuter), inner As IEnumerable(Of TInner), comparer As Predicate(Of TOuter, TInner), resultSelector As Func(Of TOuter, TInner, TResult)) As IEnumerable(Of TResult)

Function Join(Of TOuter, TInner)(outer As IEnumerable(Of TOuter), inner As IEnumerable(Of TInner), comparer As Predicate(Of TOuter, TInner)) As IEnumerable(Of (TOuter, TInner))

The latter option, especially, would allow also composing the former with a simple .Select() addition, and it's much easier to understand how to use. This question, for example, could be reduced to this:

Function MatchParts(materials As IEnumerable(Of materialsDefinition), components As IEnumerable(Of componentInfo) As IEnumerable(Of (String, String))
    Return materials.Join(components, Function(m, c) m.id = c.materialId).
         Select(Function(t) (t.Item2.componentName, t.Item1.name) )
End Function

And the benefit is not just in having shorter code, but also in making it easier to write and understand the first function call at all. Unfortunately, this is still a pipedream and we're stuck with the first option.

Sign up to request clarification or add additional context in comments.

8 Comments

Hello! Thank you for your input. When declaring the function As IEnumerable(Of String, String) an error appears as "Too many type arguments to 'IEnumerable(Of T)'
And at the Return line this error appears: ''Join' is not a member of 'IEnumerable(Of myClass.materialsDefinition)'
For the first comment, you're missing some parentheses. The answer uses As IEnumerable(Of (String, String) ), and that extra set of parentheses inside is significant. For the second, make sure you're importing System.Linq.
thanks, i tried again for the first comment, and this message appears: "Array bounds cannot appear in type specifiers). If I declare it as IEnumerable(Of String) it works correctly.
for the second comment, i think the problem is the .NET framework. For this project I am using .NET 2.0, when I changed it to .NET 3.5 and importing System.Linq, a different message error showed up: "ArgumentNullException: Overload resolution failed because no accessible 'Join' accepts this number of arguments
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.