Matt
Matt

Reputation: 1570

VB.NET Accessing Class Variables in Dictionary

I'm not sure of the syntax necessary to access a class's attributes inside of a Dictionary declaration.

Public food As New Dictionary(Of String, cheese) From
{
    {"cheese1", New cheese},
    {"cheese2", New cheese},
    {"cheese3", New cheese}
}

Public Class cheese
    Public info As New Dictionary(Of String, Array) From
    {
        {"attributes1",
            {New Dictionary(Of String, String) From
                {
                    {"name", "test"},
                    {"taste", vbNullString},
                    {"color", vbNullString}
                }
            }
        },
        {"attributes2",
            {New Dictionary(Of String, String) From
                {
                    {"name", "test"},
                    {"taste", vbNullString},
                    {"color", vbNullString}
                }
            }
        }
    }
End Class

So if I want to test it and use MsgBox() how do I trickle down to pull, say, name in food > cheese1 > info > attributes2 > name?

EDIT: I just realized that Array in info needs to be a Dictionary for an associative array, so please ignore that error and just assume it is a Dictionary for this question's sake.

Upvotes: 1

Views: 1265

Answers (2)

Cᴏʀʏ
Cᴏʀʏ

Reputation: 107526

Well, here's how to get there (taking your Array comment into account):

Dim name As String = food("cheese1").info("attributes2")("name")

If you left that inner dictionary as <String, Array> then you would have this, which would return the 0th dictionary's "name" value:

Dim name As String = food("cheese1").info("attributes2")(0)("name")

But as I hinted at in my comment, this is really poor design. Here would be one way to redo this:

Dim food As New Food()
food.CheeseAttributes.Add(New Cheese("Cheddar", "Awesome", "Yellow"))
food.CheeseAttributes.Add(New Cheese("Pepperjack", "Spicy", "White"))

This can be accomplished by refactoring your classes into this:

Public Class Food

    Private _cheeseAttributes As IList(Of Cheese)

    Public Sub New()

    End Sub

    Public ReadOnly Property CheeseAttributes() As IList(Of Cheese)
        Get
            If _cheeseAttributes Is Nothing Then
                _cheeseAttributes = new List(Of Cheese)()
            End If
            Return _cheeseAttributes
        End Get
   End Property

End Class

Public Class Cheese

    Private _name As String
    Private _taste As String
    Private _color As String

    Public Sub New (ByVal name As String, ByVal taste As String, ByVal color As String)
        Me.Name = name
        Me.Taste = taste
        Me.Color = color
    End Sub

    Public Property Name() As String
        Get
            Return _name
        End Get
        Set(ByVal value As String)
            _name = value
        End Set
    End Property

    Public Property Taste() As String
        Get
            Return _taste
        End Get
        Set(ByVal value As String)
            _taste = value
        End Set
    End Property

    Public Property Color() As String
        Get
            Return _color
        End Get
        Set(ByVal value As String)
            _color = value
        End Set
    End Property
End Class

There are probably better ways yet, but it's just here for illustration.

Upvotes: 2

JTeagle
JTeagle

Reputation: 2196

Providing some methods to help extract items would help, but I believe the syntax as you have it would be

food.Item("cheese1").info.Item("attributes2")(0).Item("name")

Upvotes: 0

Related Questions