F#互操作中的一招
当我尝试破解.CAB文件的时候, 我发现F#里面的COM交互不同于C#。
在从"COM"选项卡增加了"Microsoft Shell Controls And Automation"之后,C#里面的实例代码像下面的代码。
bool ExpandCabFile(string CabFile,string DestDir) { if (!Directory.Exists(DestDir))return false; Shell sh = new Shell(); Folder fldr =sh.NameSpace(DestDir); foreach (FolderItem f insh.NameSpace(CabFile).Items()) fldr.CopyHere(f, 0); return true; }
把C#翻译成F#应该是很简单的事。但是事实证明Shell不能被创建,因为它是一个接口!是的,你没有在读一个错误。如果你使用Object Viewer, Shell确实是一个接口。
C#这边可以使用 CoClass特性,因此新的语句调用到ShellClass。事实上, 你不能在C#代码里实例化ShellClass。
[CoClass(typeof(ShellClass))]
[Guid("866738B9-6CF2-4DE8-8767-F794EBE74F4E")]
public interface Shell :IShellDispatch5
{
}
在F#这边,你必须创建ShellClass来代替Shell。所以如果你想转换包含COM组件的C#代码到F#代码。通过Coclass特性试着找到真正的类。完整的F#代码如下所示:
let shell = new ShellClass()
let folder =shell.NameSpace(Path.GetDirectoryName(fn))
let fileName= Path.GetFileName(fn)
let currentFolder =
if not(Directory.Exists currentFolder)then
Directory.CreateDirectorycurrentFolder |> ignore
for item inshell.NameSpace(fn).Items()do
folder.CopyHere(item,0)
原文链接:http://apollo13cn.blogspot.com/2012/04/trick-in-f-interop.html