让 VBA 类模块的属性 - 是否可以有多个参数?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/13823367/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Let property of VBA class modules - is it possible to have multiple arguments?
提问by mattboy
My understanding of using the Let property in a class module so far is that you set it up in the class modules like this:
到目前为止,我对在类模块中使用 Let 属性的理解是,您可以像这样在类模块中设置它:
Dim pName as String
Public Property Let Name(Value As String)
pName = Value
End Property
And then you after you've created an object of this class you can set this property like so:
然后你在你创建了这个类的对象之后,你可以像这样设置这个属性:
MyObject.Name = "Larry"
Question: Is it possible to somehow enter multiple arguments into a class property? For instance:
问题:是否可以以某种方式在类属性中输入多个参数?例如:
Dim pFirstName as String, pLastName as String
Public Property Let Name(FirstName As String, LastName As String)
pFirstName = FirstName
pLastName = LastName
End Property
How would you then go about setting this property outside the class?
那么你将如何在课堂之外设置这个属性?
MyObject.Name = ??
Or is this just plain not possible to do?
或者这只是不可能做到的?
采纳答案by InContext
As per your comment if you would prefer to encapsulate this logic then you can use something similar to the below.
根据您的评论,如果您希望封装此逻辑,则可以使用类似于以下内容的内容。
Below includes the sub and function. The function returns a Person object:
下面包括子和函数。该函数返回一个 Person 对象:
Public Sub testing()
Dim t As Person
Set t = PersonData("John", "Smith")
End Sub
Public Function PersonData(firstName As String, lastName As String) As Person
Dim p As New Person
p.firstName = firstName
p.lastName = lastName
Set PersonData = p
End Function
Person Class:
人物等级:
Dim pFirstName As String, pLastName As String
Public Property Let FirstName(FirstName As String)
pFirstName = FirstName
End Property
Public Property Get FirstName() As String
FirstName = pFirstName
End Property
Public Property Let LastName(LastName As String)
pLastName = LastName
End Property
Public Property Get LastName() As String
LastName = pLastName
End Property
回答by
I realise there already are 2 workarounds but I thought answering your original question was worth giving a shot due to the amount of views this question is receiving.
我意识到已经有 2 种解决方法,但我认为回答您最初的问题值得一试,因为这个问题收到的观看次数很多。
The answer to
的答案
Is it possible to have multiple arguments in the Let Property in VBA?
VBA 的 Let 属性中是否可以有多个参数?
is
是
YES! It's possible.
是的!这是可能的。
First let's talk about the GET property. Consider this being the Class1
首先让我们谈谈 GET 属性。考虑这是Class1
Private firstName as String
Private lastName as String
Public Property Get Name() As String
Name = firstName & " " & lastName
End Property
The Name
property will return the full name, that's great but how to use the Let
property to assign firstName
& lastName
in one go?
该Name
属性将返回全名,这很好,但是如何使用该Let
属性一次性分配firstName
&lastName
呢?
Side note: You could pass a single string separated with a special character and split it inside the body of the Let
and assign the first
and last
namesbut forget that, let's get it done properly...
旁注:您可以传递一个用特殊字符分隔的单个字符串,并将其拆分到 的主体内Let
并分配first
和last
名称,但忘记了这一点,让我们正确完成它...
OK, in VBA the default Let
property for the current setup would take 1 parameter and assign it to either first or last name...
好的,在 VBALet
中,当前设置的默认属性将采用 1 个参数并将其分配给名字或姓氏...
Something like:
就像是:
Public Property Let Name(value As String)
firstName = value
End Property
Rule: the Get
takes no parameters and the Let
takes one. That is very logical because the Get
returns the underlying value but the Let
needs to grab a value from somewherein order to assign it to the data it's representing. Worth remembering at this point that the Let
property is assigned via the =
sign ie. myObject.Name = "IdOnKnuu"
规则:Get
不带参数,Let
带一个。这是非常合乎逻辑的,因为它Get
返回底层值,但Let
需要从某个地方获取一个值,以便将它分配给它所代表的数据。值得记住的是,该Let
属性是通过=
符号 ie分配的。myObject.Name = "IdOnKnuu"
we know that if we stay consistent with the above rule, theoretically we should be able to add one parameter to the Get
and one more to the Let
.
我们知道,如果我们留在上面的一致规律,从理论上我们应该能够一个参数添加到Get
和更多的一到Let
。
Let's forget the Let
- comment it out for now- and add a parameter to the Get
property.
让我们忘记Let
-现在将其注释掉- 并向Get
属性添加一个参数。
Private firstName As String
Private lastName As String
Public Property Get Name(first As String) As String
Name = firstName & " " & lastName
End Property
'Public Property Let Name(value As String)
' firstName = value
'End Property
Going back to the Module1
create an instance of Class1
and type c.Name(
回到Module1
创建Class1
和类型的实例c.Name(
oh, intelli-sense expecting something? Awesome!
哦,智能感知期待什么?惊人的!
At this point it's worth understanding that our Get
property returns first + last
which are both empty at the moment, so it doesn't matter what you are going to pass to the c.Name()
it will return an empty string.
在这一点上,值得理解的是,我们的Get
属性目前返回first + last
的都是空的,因此无论您要传递给c.Name()
它什么,它都会返回一个空字符串。
Ok, let's uncomment and tweak the Let
property now...
好的,让我们Let
现在取消注释并调整属性...
Side node: if you jump back to Module1
and type c.
and don't get intelli-sense it pretty much means that something in Class1
is broken... We already know - it's the Let
property that's causing it
侧节点:如果你跳回Module1
并输入c.
并且没有获得智能感知,这几乎意味着里面的东西Class1
坏了......我们已经知道 - 这Let
是导致它的属性
We have added a parameter to the Get
property, let's do the same with the Let
property...
我们给Get
属性添加了一个参数,让我们对属性做同样的事情Let
......
Public Property Let Name(first As String, value As String)
firstName = value
End Property
Let's go back to the Module1
and try to use the Let
property:
让我们回到Module1
并尝试使用该Let
属性:
Remember, how you have used the Let
property before? You needed to assign it a value
请记住,您Let
之前是如何使用该物业的?你需要给它赋值
c.Name = "John"
But now, your Let
property is expecting an extra parameter first as String
.
但是现在,您的Let
财产需要一个额外的参数first as String
。
Why don't we try this:
我们为什么不试试这个:
c.Name("John") = "Smith"
Hey! that compiles and runs (a quick F5)
嘿!编译和运行(快速F5)
Great, let's check the results!
太好了,让我们看看结果!
Debug.print c.Name("John")
Uhm... that only shows Smith
in the Immediate Window (Ctrl+G)... Not exactly what we were looking for....
嗯...只显示Smith
在即时窗口 ( Ctrl+ G)... 不完全是我们要找的....
Going back to the Let
property we notice that we are grabbing 2 values via arguments but we only make use of one of them? We have the 2 different values coming in to the function, right? Let's treat the first one as the firstName
and the second one as lastName
回到Let
属性,我们注意到我们通过参数获取了 2 个值,但我们只使用了其中一个?我们有两个不同的值进入函数,对吗?让我们把第一个当作firstName
第二个当作lastName
Public Property Let Name(first As String, last As String)
firstName = first
lastName = last
End Property
Going back to Module1
回到 Module1
Sub Main()
Dim c As New Class1
c.Name("John") = "Smith"
Debug.Print c.Name("John")
End Sub
and re-running out current code gives us what we need ... it prints John Smithbut wait!!! why do we have to pass the first name in order to retrieve the full name?
并重新运行当前代码为我们提供了我们需要的东西......它打印了约翰史密斯但是等等!!!为什么我们必须通过名字才能检索全名?
Ha! The trick to this is to make the first parameters of both properties Optional
哈!诀窍是使两个属性的第一个参数Optional
Summarising, the code:
总结一下,代码:
Class1.cls
类1.cls
Private firstName As String
Private lastName As String
Public Property Get Name(Optional first As String) As String
Name = firstName & " " & lastName
End Property
Public Property Let Name(Optional first As String, last As String)
firstName = first
lastName = last
End Property
Module1.bas
模块1.bas
Sub Main()
Dim c As New Class1
c.Name("John") = "Smith"
Debug.Print c.Name ' prints John Smith
End Sub
So basically the assignment of two (or more) values through the Let
property is possible in VBA. The thing that may throw you off a bit is the Syntax for it but I hope my explanation in this answer has helped you understand where things come from and why.
因此,基本上可以在 VBA 中通过属性分配两个(或多个)值Let
。可能会让你有点失望的是它的语法,但我希望我在这个答案中的解释能帮助你理解事物的来源和原因。
The Get
property takes an optional parameter- it's really just a dummy parameter... it's not used anywhere within the Get
property but it's allowing us to get the desired Let
signature and allows us to pass two parameters to it. It also grants the easy to remember c.Name
syntax.
该Get
属性采用一个可选参数——它实际上只是一个虚拟参数……它没有在Get
属性中的任何地方使用,但它允许我们获得所需的Let
签名并允许我们向它传递两个参数。它还提供易于记忆的c.Name
语法。
The call
电话
Debug.Print c.Name("first")
is still possible, however the "first"
parameter just acts like a dummy and has no effect on the actual underlying data. It's a dummy and has no effect on the actual data - dump it and use:
仍然是可能的,但是该"first"
参数就像一个虚拟对象,对实际的基础数据没有影响。这是一个虚拟的,对实际数据没有影响 - 转储它并使用:
Debug.print c.Name
definitely more convenient :)
绝对更方便:)
回答by KacireeSoftware
Use as Public Sub procedure within the class to perform this:
在类中用作 Public Sub 过程来执行此操作:
Public Sub testing()
Dim myPerson As New Person
myPerson.SetName "KaciRee", "Software"
End Sub
Person Class:
人物等级:
Dim pFirstName As String, pLastName As String
Public Property Let FirstName(FirstName As String)
pFirstName = FirstName
End Property
Public Property Get FirstName() As String
FirstName = pFirstName
End Property
Public Property Let LastName(LastName As String)
pLastName = LastName
End Property
Public Property Get LastName() As String
LastName = pLastName
End Property
Public Sub SetName(FirstName As String, LastName As String)
pFirstName = FirstName
pLastName = LastName
End Sub