【发布时间】:2022-03-26 00:37:08
【问题描述】:
我目前正在尝试使用 win32com 在 python 中复制一些 VBA 代码。此特定代码使用TypeName,并且我在下面使用 Excel(不是我正在与之交互的实际程序)制作了 MWE:
' VBA script that will print "Worksheet" as the TypeName
Public Sub GetActiveSheet()
MsgBox TypeName(ActiveSheet)
End Sub
使用win32com.client.gencache.EnsureDispatch 似乎可以实现某些事情,例如:
excel_gc = win32com.client.gencache.EnsureDispatch("Excel.Application")
sheet_gc = excel_gc.ActiveSheet
#> <win32com.gen_py.Microsoft Excel 15.0 Object Library._Worksheet instance at 0x83075408>
type(sheet)
#> <class 'win32com.gen_py.00020813-0000-0000-C000-000000000046x0x1x8._Worksheet._Worksheet'>
不幸的是,我不得不在这个应用程序中使用win32com.client.dynamic.Dispatch,因为它似乎使用了工厂设计模式,经常返回“AnyObject”。当我使用 dynamic.Dispatch 时,我不再有 COMObject 类型的信息:
excel = win32com.client.dynamic.Dispatch("Excel.Application")
sheet = excel.ActiveSheet # <COMObject <unknown>>
type(sheet)
#> <class 'win32com.client.dynamic.CDispatch'>
有没有人能够阐明如何从win32com.client.dynamic.Dispatch 的<COMObject <unknown>> 对象中获取类型信息?谢谢!
【问题讨论】:
-
type有什么用? vba 中是否有任何代码根据类型执行的操作? -
有一个switch语句可以根据工厂返回的对象改变行为。例如,
ShapeFactory()可以返回Square或Circle,如果是Square,那么我想要该区域,如果是Circle,我想要周界。当使用win32com.client.gencache.EnsureDispatch时,显示的类型将是<COMObject <AnyShape>>而不是<COMObject <Square>> -
VB/VBA 的 TypeName 的真正工作原理从未在 AFAIK 中记录过。它是众所周知的 VBA 类型(如整数或布尔值等)stackoverflow.com/questions/38365630/… 和“其他”类型的动态发现的混合。动态发现基于 IProvideClassInfo/IProvideClassInfo2 接口(可能还有其他一些技巧)你在这里有一个 delphi 示例:delphigroups.info/2/2f/262023.html
-
谢谢@SimonMourier,我会看一下delphi代码并尝试拼凑一个python等价物。如果我得到它的工作,我会发布一个答案