简体   繁体   中英

Looping Through a dictionary with custom object items

I'm sure I'm missing the huge elephant in the room but I keep getting errors on this. I'm creating a public dictionary called Prompts and filling it with a custom class object in the sub below.

Public Sub SetPromptControls()
Dim PromptsRange As Range
Dim PromptRow As Range

Set PromptsRange = Range("LookUpTablePrompts")
Dim NewPrompt As clsPrompt
For Each PromptRow In PromptsRange.Rows
    Set NewPrompt = New clsPrompt
    NewPrompt.Name = PromptRow.Cells(1, 1)
    NewPrompt.ControlType = PromptRow.Cells(1, 2)
    NewPrompt.ComboboxValues = PromptRow.Cells(1, 3)
    NewPrompt.HelpText = PromptRow.Cells(1, 4)
    NewPrompt.TabIndex = PromptRow.Cells(1, 5)
    NewPrompt.ColumnIndex = PromptRow.Cells(1, 6)
    NewPrompt.TableIndex = PromptRow.Cells(1, 7)
    NewPrompt.ControlName = PromptRow.Cells(1, 8)


    Me.Prompts.Add NewPrompt.ControlName, NewPrompt
Next
End Sub

Now I'm trying to loop through the dictionary I just made in this next sub which is inside the same class. The problem is the for each loop keeps giving me object errors

Public Sub SetProductPromptMapping()
Dim ProductPromptMappingRange As Range
Dim SKURange As Range
Dim SKUPromptMapRow As Integer
Dim MapRow As Range
Dim Key As Variant
Dim Prompt As clsPrompt
Set ProductPromptMappingRange = Range("LookUpTablePromptMap")
Set SKURange = ProductPromptMappingRange.Find(PromptsForm.SKU, LookIn:=xlValues)
SKUPromptMapRow = SKURange.Row - 2

For Each Key In Prompts.Keys
    Set Prompt = New clsPrompt
    Prompt = Key
    Me.ProductPromptMappingRow.Add Prompt.ControlName, ProductPromptMappingRange.Cells(SKUPromptMapRow, Prompt.TableIndex).Value
Next

End Sub

Ultimately I would like to loop through my Prompts dictionary and cast the current item back to my clsPrompt class object so that I can access its properties.

As Comintern correctly points out , you've been bit by a common mistake - trying to assign an object reference without the Set keyword. Here's the smallest example I can come up with that demonstrates the problem:

Option Explicit

Public Sub DoSomething()
    Dim foo As MyClass
    foo = New MyClass
End Sub

Here there's a local foo object variable that's assigned a reference ( = New MyClass ), but because the assignment is made without the Set keyword, running this would raise a runtime error 91:

Object variable or With block variable not set

Your code has that exact same issue:

Dim Prompt As clsPrompt
'...
'more code
'...
Prompt = Key

The code happily compiles , but will consistently raise that runtime error 91 when executed .

This mistake is common enough (just look at how many questions involve runtime error 91 right here on Stack Overflow), that I've decided to implement an inspection for it in the latest version of Rubberduck , an open-source COM add-in for the VBE that can help you clean up your code (I'm managing the project):

Rubberduck代码检查

Object variable 'foo' is assigned without the 'Set' keyword

As far as Rubberduck can tell, this variable is an object variable, assigned without the 'Set' keyword. This causes run-time error 91 'Object or With block variable not set'.

Rubberduck would have caught that error =)


What it wouldn't have caught though, is that it doesn't make much sense to assign Prompt a new reference, just to re-assign it to some Variant right away. Again as Comintern correctly points out , you need to Set Prompt = Prompts(Key) here.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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