【问题标题】:Excel Vba error: Definitions of property procedures for the same property are inconsistentExcel Vba报错:同一属性的属性过程定义不一致
【发布时间】:2013-08-26 14:26:00
【问题描述】:

这一定很明显,但我被困住了,所以也许你们可以帮助我。

考虑 VBA 自定义对象中的以下代码:

Private pSkipTrade As Boolean
Property Let SkipTrade(value As Double):
    If value = 0 Then
        pSkipTrade = False
    Else
        pSkipTrade = True
    End If
End Property

Public Property Get SkipTrade() As Boolean
    SkipTrade = pSkipTrade
End Property

谁能帮帮我?

提前通知!

【问题讨论】:

  • @DavidZemens。信不信由你。我刚刚学会了如何做到这一点!

标签: excel vba properties custom-object


【解决方案1】:

Let 参数必须与 Get 属性的返回类型相匹配。见this

所以你需要将Property Let中的参数改为布尔类型:

Private pSkipTrade As Boolean
Property Let SkipTrade(value As Boolean) '<--Parameter is Boolean type
   pSkipTrade = value 
End Property

Public Property Get SkipTrade() As Boolean
    SkipTrade = pSkipTrade
End Property

然后将您在 Let 属性中的逻辑移动到使用该属性的代码中:

If price = 0 Then
    SkipTrade = False
Else
    SkipTrade = True
End If

【讨论】:

    【解决方案2】:

    试试这个:

    Private pSkipTrade As Boolean
    Public Property Let SkipTrade(lSkipTrade As Boolean)
        pSkipTrade = lSkipTrade
    End Property
    Property Get SkipTrade() As Boolean
       SkipTrade = pSkipTrade
    End Property
    

    在您的代码中的其他地方,您正在使用另一个变量(例如,value)来设置此属性。如果此变量不是 Boolean 类型(例如,LongDoubleDecimal),那么您可以执行以下操作:

    Sub Test()
    Dim MyObject As Object
    Dim Value As Double               '## or, whatever
    
    '# CREATE THE CLASS OBJECT
    Set MyObject = New cMyObject  '## Modify to be your correct Type
    
    Value = Application.InputBox("Enter any number")
    
    '# ASSIGN THE PROPERTY VALUE BASED ON A LOCAL VARIABLE/LOGIC
    '  use boolean logic to test whether "value = 0"
    '  a non-zero value will return "True"
    MyObject.SkipTrade = Not (CDbl(Value) = 0)
    
    '# Display the value, so you can see that this is working correctly:
    MsgBox "The value of SkipTrade is: " & MyObject.SkipTrade
    
    End Sub
    

    如果您有多个条件,最好在对象的属性分配期间使用Function 调用返回属性值。

    您可以调用如下函数:

    MyObject.SkipTrade = CheckSkipTrade(value)
    

    在您的主代码模块中使用这样的函数,可以对其进行修改以包含您可能需要合并的任何逻辑:

    Function CheckSkipTrade(value) As Boolean
    Dim myVal as Boolean
        If IsNumeric(value) Then
           'returns true or false test whether 'value' = 0.
           myVal = Not(CDbl(value) = 0)
        Else:
            myVal = False
    
        End If
    
        '# Return the value of the function test:
        CheckSkipTrade = myVal
    End Function
    

    请注意,在上面的示例中,您正在直接对MyObject 类对象的SkipTrade 属性进行赋值,这是非常明确的——不是隐藏的?相反,您的方法本质上调用隐藏在对象模块中的子例程,该子例程为属性分配值。它有效吗?是的。这是最好的方法吗?我不这么认为;这是一种非常令人困惑的编码方式,这将使以后的故障排除(尤其是如果您将此项目交给其他人时)变得更加困难。

    显式编码优于隐式编码

    【讨论】:

    • 但是如果 'lSkipTrade' 或 'value' 是双精度值呢?
    • @AMariani 它不能是双精度的,因为您已经声明了属性pSkipTrade As Boolean。如果您尝试将任何非 bool 类型分配给此属性,您将收到不匹配错误。
    • 有办法解决吗?我实际上想将我的 pSkipTrade 定义为真或假,具体取决于“值”是否为零(以及其他类似检查)。
    • 我认为您不了解如何使用类对象 :) 我会为您更新更多信息。
    • 我确实开始了解对象。你能看出我提出的解决方案有什么问题吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-05-30
    • 2017-06-14
    • 2019-11-13
    • 1970-01-01
    • 2019-09-12
    • 1970-01-01
    相关资源
    最近更新 更多