Передача параметра в функцию для создания имени переменной - PullRequest
0 голосов
/ 06 ноября 2019

Я хочу иметь возможность использовать некоторые глобальные переменные в своей рабочей книге и в коде ThisWorkbook. Я объявил следующие переменные

Public position_1 as string
Public position_2 as string

Если я хочу увидеть значение этих переменных, я считаю, что это необходимочтобы быть полностью квалифицированным, поэтому

Debug.Print ThisWorkbook.position_1
Debug.Print ThisWorkbook.position_2

Я написал UDF, который я передам в целое число, чтобы представить, какую переменную я ищу. Я буду передавать только одно число, а не полное имя переменной. Я пытаюсь найти способ использовать это целое число для объединения с "position_" для отображения значения глобальной переменной ThisWorkbook.position_1, ThisWorkbook.position_2 и т. Д.

Возможно ли это?

 Function Test_Global_Var(position as Integer)
            Dim variable_name As String
            variable_name = "position_" & position
            Debug.Print ThisWorkbook.variable_name
        End Function

Поэтому, когда я звоню

Test_Global_Var(1) 

, в моем ближайшем окне должно отображаться значение

ThisWorkbook.position_1

Ответы [ 2 ]

0 голосов
/ 07 ноября 2019

Приведенный ниже код создает следующий отладочный вывод

2 values defined.
ThisWorkbook.Position(0)
First Value
ThisWorkbook.Position(1)
Second Value

Он использует личный массив в книге с именем m_position. Доступ к содержимому осуществляется глобальным свойством ThisWorkbook.Position(index).

В модуле имеется следующий код:

Option Explicit

Public Sub Test()    
    If ThisWorkbook.NoValues Then
        ThisWorkbook.FillValues "First Value", "Second Value"
    End If

    Debug.Print CStr(ThisWorkbook.Count) & " values defined."

    Test_Global_Var 0
    Test_Global_Var 1
End Sub

Public Sub Test_Global_Var(ByVal index As Long)
    ' Part of a UDF
    Debug.Print "ThisWorkbook.Position(" & CStr(index) & ")"
    Debug.Print ThisWorkbook.Position(index)

End Sub

В ThisWorkbook имеет следующий код:

Option Explicit

Private m_position() As Variant

Private Sub Workbook_Open()
    Call DefaultValues
End Sub


Public Property Get Position(ByVal index As Long) As Variant
    Position = m_position(index)
End Property

Public Sub DefaultValues()
    m_position = Array("First", "Second")
End Sub

Public Sub FillValues(ParamArray args() As Variant)
    m_position = args
End Sub

Public Property Get Count() As Long
    Count = UBound(m_position) - LBound(m_position) + 1
End Property

Public Property Get NoValues() As Boolean
    On Error GoTo ArrUndefined:
    Dim n As Long
    n = UBound(m_position)
    NoValues = False
    On Error GoTo 0
    Exit Sub
ArrUndefined:
    NoValues = True
    On Error GoTo 0
End Property

PS. В VBA никогда не используйте Integer, а вместо этого используйте Long. Integer - это 16-битный тип, а Long - это стандартный 32-битный тип, который все другие языки программирования считают integer.

0 голосов
/ 06 ноября 2019

Можно рассмотреть глобальную словарную переменную и передать через нее данные из UDF. Сначала добавьте ссылку на Microsoft Scripting Runtime:

enter image description here

Таким образом, создайте словарь так:

Public myDictionary As Dictionary

Для инициализации myDictionary переменная, рассмотрите добавление ее к событию Workbook_Open:

Private Sub Workbook_Open()
    Set myDictionary = New Dictionary
End Sub

Тогда UDF будет выглядеть так:

Public Function FillDicitonary(myVal As Long) As String

    If myDictionary.Exists(myVal) Then
        myDictionary(myVal) = "position " & myVal
    Else
        myDictionary.Add myVal, "position " & myVal
    End If
    FillDicitonary = "Filled with " & myVal

End Function

И он будет перезаписывать каждый ключ в словаре,если это существует. В конце значения могут быть напечатаны:

Public Sub PrintDictionary()

    Dim myKey As Variant
    For Each myKey In myDictionary
        Debug.Print myDictionary(myKey)
    Next

End Sub
...