首页 > 解决方案 > 如何使用查找功能

问题描述

我最近编写了一些代码来从用户表单文本框中获取输入并在我的数据库中搜索它。如果找到,我希望它返回值并将其插入单元格 A1149;我已经编写了以下代码,但它给了我错误 #424“需要对象”。我对 VBA 非常陌生,因此非常感谢任何和所有帮助。

Private Sub CMDSearch_Click()

     Dim pesquisa As Range

     Set pesquisa = Worksheets("Petrobras").Activate.Range("$W:$W") _
         .Find(What:=Opp_Num_Search.Value, LookIn:=xlValues, Lookat:=xlWhole).Activate

     Worksheets("Petrobras").Range(A1149).Value = pesquisa.Value

     UserForm1.Hide

End Sub

标签: excelvba

解决方案


Range.Activate不返回任何东西,就像一个Sub过程:

Public Sub DoSomething()
    ' does something...
End Sub

如果你这样做了Set foo = DoSomething.Something,你会得到同样的错误:一个对象是必需的,否则该.Something成员调用是非法的(除了现在错误将在编译时而不是运行时,因为绑定是如何工作的)。

Set pesquisa = Worksheets("Petrobras").Activate...

你不想要Activate任何床单。

问题的一部分是隐式的后期绑定:Worksheets返回一个Object,所以你之后写的所有东西,所有这些链接的成员调用,只能在运行时解决。

Worksheet通过声明一个显式变量使其成为早期绑定:

Dim sheet As Worksheet
Set sheet = Worksheets("Petrobras")

现在如果你想激活它,你可以做sheet.Activate(​​但你不需要)。如果您想Range从该工作表中获取一个,您可以.Range拨打会员电话,IDE 现在将帮助您

Dim result As Range
Set result = sheet.Range("$W:$W").Find(...)

永远不要将任何成员调用链接到Range.Find返回的内容。如果搜索出现了结果,那么您就有了一个Range对象。如果没有,您有Nothing- 并且针对任何成员调用Nothing将始终引发运行时错误 91。

首先验证搜索结果:

If result Is Nothing Then
    MsgBox "Could not find '" & Opp_Num_Search.Value & "' in column W."
    Exit Sub
End If

或者:

If Not result Is Nothing Then
    sheet.Range("A1149").Value = result.Value
End If

请注意,这A1149是表示单元格地址的字符串文字,因此必须用双引号 ( ") 括起来。如果它不在双引号中并且它看起来像一个有效的变量名,VBA 会将其视为 ..a 变量......这将导致另一个错误(1004),因为使用一个值Range会相当不愉快。Variant/Empty

为了防止 VBA 使用拼写错误“声明”动态变量(并导致难以找到的错误),请确保您Option Explicit在项目中的每个模块的最顶部都有。

最后一件事:

 UserForm1.Hide

这隐藏了 的默认实例UserForm1它可能是也可能不是显示的当前对象/实例 - 表单本身无法知道它是如何显示的:

UserForm1.Show '<~ shows the default instance
With New UserForm1
    .Show '<~ shows a new (non-default) instance
End With

因此,您应该避免在表单的代码隐藏中引用默认实例。改用Me

Me.Hide

这样,您指的是当前显示的表单的任何实例,无论它是否是默认实例。有关用户表单的更多信息、提示、陷阱和常见错误,请参阅UserForm1.Show

请注意,Rubberduck 有相当多的检查可以识别并警告您(并且通常会自动修复)大多数这些问题。Rubberduck 是我管理的一个免费和开源的 VBIDE 插件项目。


推荐阅读