【问题标题】:Calling a Private Sub from another module从另一个模块调用私有子
【发布时间】:2018-11-22 10:19:45
【问题描述】:

我有两个模块,Module1 和 Module2。

在模块 1 中:

Private Function myCheck() As Boolean

if [Operation] = [Something] then

myCheck = True
Else
myCheck = False
End if

End Sub

在Module2中,我想在Module 1中运行myCheck sub,然后再做一个操作:

Private Sub Execute()

[Operation 1]

If myCheck = True Then

[Operation 2]
Else
[Operation 3]

End If
End Sub

它不起作用。如果我将 Private Function myCheck 放在同一个模块中,那么它就可以工作。是否有特殊的方法可以从另一个模块调用子或函数?

【问题讨论】:

  • Private 更改为Public,或者真的只是删除Private,它将被公开。
  • 这是唯一的方法吗?私有化的全部意义在于对用户隐藏它..
  • 设为Private 表示该函数可用于存储它的模块。
  • 好的 - 把它放在答案中,我会标记为正确的。谢谢
  • @Oday 如果您想向用户隐藏它,那么您应该将该信息添加到您的问题中。请参阅 Stax 的解决方案答案

标签: vba excel


【解决方案1】:

您可以使用Application.Run 来执行此操作:

Application.Run "Module1.myCheck"

如果用户显示宏对话框 (Alt+F8),宏将对用户保持“不可见”,因为它仍然是私有的。

编辑#1

第二种选择是在Sub 中引入一个虚拟变量作为可选参数,如下所示:

Public Sub notVisible(Optional dummyVal As Byte)
    MsgBox "Im not visible because I take a parameter, but I can be called normally."
End Sub

这也将隐藏宏对话框中的宏 (Alt+F8),但现在可以按通常的方式调用它。

【讨论】:

  • 注意:Optional 参数不能是Variant,以便从宏框中隐藏子
  • @chris neilsen 是的,感谢您指出这一点。但是,由于我们在这种情况下使用了一个虚拟变量,所以我只推荐Byte,因为它占用的内存最少。
【解决方案2】:

对模块 1 使用选项私有模块,然后在模块 2 中:

对于一个;用它所在的模块来限定你正在调用的内容,如下所示:

Module1.myCheck()

对于一个私人子;使用 Application.Run 并使用它所在的模块限定您正在调用的内容,如下所示:

Application.Run ("Module1.myCheck")

使用私有模块隐藏它包含在开发人员>宏列表中的子/s。


进一步阅读:-)

通读下面代码中的 cmets,了解哪些功能有效,哪些无效。 要自己确认这些行为: 创建一个新的 Excel,打开 Developer > Visual Basic,插入 3 个模块。 将以下代码块复制到相关模块中。

'In Module1
Option Explicit

Sub ScopeTrials()

'NOTES:
'   Only NormalSubIn_NormalModule shows in Developer > Macros.

'   As the default without a keyword is Public I have called
'   these "Normal". I.e. you can use Public or Nothing wherever
'   Normal is.

'   A line commented out shows what doesn't work.

NormalSubIn_NormalModule
Call NormalSubIn_NormalModule
Application.Run ("NormalSubIn_NormalModule")  'Not recommended!

NormalSubIn_PrivateModule
Call NormalSubIn_PrivateModule
Application.Run ("NormalSubIn_PrivateModule")  'Not recommended!

'PrivateSubIn_NormalModule
'Call PrivateSubIn_NormalModule
'Module2.PrivateSubIn_NormalModule
'Call Module2.PrivateSubIn_NormalModule
Application.Run ("PrivateSubIn_NormalModule")  'Fails with duplicates! See Explanation
Application.Run ("Module2.PrivateSubIn_NormalModule")

'PrivateSubIn_PrivateModule
'Call PrivateSubIn_PrivateModule
'Module3.PrivateSubIn_PrivateModule
'Call Module3.PrivateSubIn_PrivateModule
Application.Run ("PrivateSubIn_PrivateModule")  'Fails with duplicates! See Explanation
Application.Run ("Module3.PrivateSubIn_PrivateModule")

'Explanation: if there is an identical sub in another Private Module, then this fails
'with Runtime Error 1004 (Macro not available or Macros Disabled), which is Misleading
'as the duplication and/or nonspecified module is the problem.
'I.e. always specify module!
'Also, this only fails when the line is actually run. I.e. Compile check doesn't find this
'when starting to Run the code.

End Sub

'In Module2
Option Explicit



Sub NormalSubIn_NormalModule()  'only THIS sub shows in Developer > Macros

    MsgBox "NormalSubIn_NormalModule"

End Sub


Private Sub PrivateSubIn_NormalModule()

    MsgBox "PrivateSubIn_NormalModule"

End Sub

'In Module3
Option Explicit
Option Private Module


Sub NormalSubIn_PrivateModule()

    MsgBox "NormalSubIn_PrivateModule"

End Sub


Private Sub PrivateSubIn_PrivateModule()

    MsgBox "PrivateSubIn_PrivateModule"

End Sub

【讨论】:

  • 使用 Option Private Module(在模块范围内)和 Public Sub ... 使 Sub 在其他模块中可见,但在 Excel 宏列表中不可见 - Alt-F8。我认为那是 OP 想要的......
猜你喜欢
  • 2015-03-10
  • 2017-04-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-08-12
  • 1970-01-01
  • 2018-10-01
相关资源
最近更新 更多