2017-10-11 434 views
0

我在VS2010中的解決方案有一個在c#項目中引用的CLI項目。我在CLI中有一個名爲do_something的抽象類。在C#中,我從它繼承了DoSomething類。我想通過傳遞c#實現作爲抽象類參數來運行C++的c#實現,但拋出了「不受語言支持」的異常。語言不支持「方法」

CLI/C++

//abstract class 
public ref class do_something{ 
    public: 
    virtual void do_it()=0; 
}; 
//using an implementation of the abstract class 
public ref class cpp_caller{ 
    public: 
    void run(do_something% doer){ 
    cout<<"run c# from c++"<<endl; 
    doer.do_it(); 
    } 
}; 

C#

//implementation of abstract class 
class DoSomething : do_something 
{ 
    public override void do_it() 
    { 
    Console.WriteLine("call from c#"); 
    } 
} 
//inside main 
DoSomething csharp_implementation = new DoSomething(); 
cpp_caller caller = new cpp_caller(); 
caller.run(csharp_implementation); 

的C++項目編譯,但編譯的C#代碼的最後一行時,編譯器會引發異常: '跑' 不被支持的語言

注意:先前的堆棧溢出解決方案沒有幫助!調用run.do_it()在c#中工作正常。最後,CLI編譯器不喜歡使用'^'或'&'通過引用將參數傳遞給run方法。

+0

它應該使用'^'。它也應該使用'^%'並在C#中使用'ref'關鍵字。請顯示你失敗的嘗試。 –

+0

當使用'^','^%'或'%^'時,cli編譯器會拋出:'.do_it'的左邊必須有class/struct/union。 –

+1

'^'是'*'管理的等價物。你需要使用' - >',而不是'.'。 –

回答

0

我假設你是從C#得到這個錯誤,而不是從C++/CLI 「不被支持的語言」。

public ref class do_something 

void run(do_something% doer) 

C#不支持此組合:C#:一種對引用類型值的跟蹤引用。

由於它是引用類型,因此C#中的do_something本身等同於C++/CLI中的do_something^。在C#中聲明一個具有ref do_something參數的方法使其在C++/CLI中爲do_something^%。對於引用類型,這就是C#支持的所有內容。

C++/CLI確實支持使用ref類作爲值:do_something本身爲您提供了堆棧語義,您可以使用do_something%作爲跟蹤引用傳遞它,但在C#中都沒有使用它們。

傳遞ref類的正確方法是使用^,並使用gcnew初始化變量。這是其他.Net語言所做的,所以如果你想從他們那裏調用,你需要遵循他們的規則。正如你在評論中指出的那樣,切換到^解決了你的問題。


其他說明:

這就是C++的方式來聲明一個抽象類,我根本不知道在C++/CLI仍然支持。如果您想以管理方式(我會推薦)宣佈它,請在類和方法上使用關鍵字abstract

public ref class do_something abstract 
{ 
public: 
    virtual void do_it() abstract; 
};