2009-12-01 15 views
3

我正在研究Boo,並認爲這將是一個有用的練習,可以嘗試轉換一些使Excel自動運行的VB腳本(本例中爲2007)。許多事情似乎很容易翻譯,但是我在選擇範圍時遇到了很多麻煩 - 每當我嘗試獲取或設置它們時,我都會找到一個TargetInvocationException成員。Boo - Excel自動化,故障選擇範圍

下面是我在booish運行(減少)例如:

def CreateInstance(progid): 
    type = System.Type.GetTypeFromProgID(progid)  
    return type() 

xl as duck = CreateInstance("Excel.Application") 
xl.Visible = true 
xl.Workbooks.Add 

sht as duck = xl.ActiveSheet 
#Next line throws exception 
rng as duck = sht.Range("A1") 

有些事情做工精細,如設置紙張的名稱屬性等等,但我怎麼用範圍工作?是否有一些VB隱藏的特殊方法需要調用,如果有的話,我將如何去查找這些方法?

乾杯,

Lenny。

回答

3

Range實際上是一個屬性,它是一個有點特殊的屬性,它用作索引器,這意味着它具有數組或字典式的語義。在大多數語言中,這意味着您可以訪問sht.Range["A1"]。這是語法糖,說實在的,訪問就像任何其他的方法,即:

sht.get_Range("A1",System.Reflection.Missing.Method) 

我試圖使用噓,紅寶石和IronRuby重複你的代碼,同時使用語法糖風格和明確的方法調用。在IronRuby中,我可以完美地工作,但只有在32位解釋器中才有。在我的配置中的常規Ruby中,它是一款32位應用程序,它也運行良好。在64位解釋器中,Range屬性從未正確解析。

因此,這讓我懷疑Boo Interactive Shell運行在64位模式下,並且互操作失敗。不幸的是,在將我的本地Boo二進制文件設置爲使用CORFLAGS.exe在32位模式下運行後,再次出現了相同的問題,所以我認爲這不是真正的問題。

什麼做的工作,雖然是明確導入Excel DOTNET互操作庫,以及互操作的服務的命名空間,就像這樣:

import Microsoft.Office.Interop.Excel 
import System.Runtime.InteropServices 

xl_type=typeof(Application).GetCustomAttributes(typeof(CoClassAttribute),true)[0].CoClass 
xl=xl_type() 
xl.Visible=true 
xl.Workbooks.Add 

然後:

xl.Range["A1","A2"].Value=12 
xl.Range["A1",System.Type.Missing].Value="Alpha" 
(xl.ActiveSheet as Worksheet).Range["A1","A2"].Value2='Whatever' 

所有這些工作,但他們基本上要求你放棄你習慣於從遲綁定(這是你的鴨子打字所做的)的「Scriptiness」。

對於大多數語言(C#4.0除外),VB/VBScript的一個不同之處在於,通常可選參數不是透明處理的,所以您在處理時需要更仔細地查看API支持可選參數的方法(用System.Type.Missing或System.Reflection等效替換它們)。你可以通過Excel interop文檔找到它,儘管如果你發現比查找更容易,你可以使用反射來標識標記爲可選的參數。

因爲Ruby有一個合理的解決方案來爲後期綁定這些對象,所以我懷疑在Boo的COM互操作場景中缺少一個功能(或bug)。

編輯補充:Sam Ng writes about indexed property support in C# 4.0;他的帖子中描述的問題也可能適用於Boo。

+0

感謝您付出如此多的努力 - 我會再調查一下! – 2009-12-03 10:38:57