2012-06-30 56 views
0

我在C++中製作一個用於語音識別的接口類,我使用的是Julius API。 http://julius.sourceforge.jp/en_index.php?q=index-en.html在C++/CLI中傳遞非靜態委託屬性函數作爲參數

那麼,我的班級有一些事件,這些事件將由Julius API觸發。 朱利葉API具有函數調用與此簽名callback_add:

int callback_add (Recog *recog, int code, void(*func)(Recog *recog, void *data), void data)

我使用一些「代理」功能調用事件,並通過這項功能callback_add。

如果屬性事件是靜態的,它可以正常工作,但如果是非靜態的,則在代理函數內不能識別屬性。

困難的是因爲我必須使用callback_add函數並且不能修改它。

下面是類與2個事件(靜態和非靜態)

部首

#ifndef FALAENGINE_H_ 
#define FALAENGINE_H_ 

#pragma once 

extern "C"{ 
#include <julius/julius.h> 
} 

namespace FalaAPI { 

    public ref class FalaEngine 
    { 
    public: 
     FalaEngine(); 
     ~FalaEngine(); 

     // Events 
     delegate void OnRecognizedDele(FalaAPI::RecoResult^ result); 
     static property OnRecognizedDele^ OnRecognized; 

     delegate void OnEngineStartDele(); 
     property OnEngineStartDele^ OnEngineStart; 

    private: 
     Recog *recog; 
     Jconf *jconf; 
    }; 
} 

#endif /* FALAENGINE_H_*/ 

#include "stdafx.h" 

using System::String; 
using System::Console; 

#include "FalaEngine.h" 
#include <windows.h> 

namespace FalaAPI{ 
    void StartOnEngineStart()(Recog *recog, void * dummy){ 
     if(FalaEngine::OnEngineStart->GetInvocationList()->Length > 0) 
      FalaEngine::OnEngineStart->Invoke(); 
    } 

    void StartOnRecognized()(Recog *recog, void * dummy){ 
     if(FalaEngine::OnRecognized->GetInvocationList()->Length > 0) 
      FalaEngine::OnRecognized->Invoke(); 
    } 

    FalaEngine::FalaEngine(){ 
     recog = j_recog_new(); 
     jconf = j_jconf_new(); 

     //Julius callback Functions 
     callback_add(recog, CALLBACK_EVENT_PROCESS_ONLINE, StartOnEngineStart, NULL); 

     callback_add(recog, CALLBACK_RESULT, StartOnRecognized, NULL); 
    } 
} 

內部StartOnEngineStart出現該問題的一個摘要功能:

錯誤C2227:' - > GetInvocationList'的左側必須指向類/結構/聯合/泛型類型

回答

0

非靜態成員分別存在於每個實例中。您尚未指定哪個實例包含要檢查的委託,您只指定了一個類(並且可能有很多實例)。

嘗試使用dummy參數傳遞您的實例。但要小心,因爲垃圾收集器會移動物體,除非您固定了它們,所以只需傳遞該地址將不起作用。您需要創建並通過GCHandle。 (注意不要漏了的GCHandle,或者你的對象將永遠不會被釋放)


像這樣的東西應該是有效的:

ref class FalaEngine; 

struct EngineHandle 
{ 
    gcroot<FalaEngine^> handle; 
    EngineHandle(FalaEngine^ engine) : handle(engine) {} 
}; 

public ref class FalaEngine 
{ 
    clr_scoped_ptr<EngineHandle> callback_ptr; 
public: 
    FalaEngine(); 
    ~FalaEngine(); 

    // Events 
    delegate void OnRecognizedDele(FalaAPI::RecoResult^ result); 
    property OnRecognizedDele^ OnRecognized; 


    delegate void OnEngineStartDele(); 
    property OnEngineStartDele^ OnEngineStart; 

private: 
    Recog *recog; 
    Jconf *jconf; 
}; 

void StartOnEngineStart(Recog *recog, void * dummy) 
{ 
    FalaEngine^ that = static_cast<EngineHandle*>(dummy)->handle; 
    that->OnEngineStart(); // C++/CLI already checks if the invocation list is empty 
} 


void StartOnRecognized(Recog *recog, void * dummy) 
{ 
    FalaEngine^ that = static_cast<EngineHandle*>(dummy)->handle; 
    that->OnRecognized(recog->get_result()); 
} 

FalaEngine::FalaEngine() 
    : callback_ptr(new EngineHandle(this)) 
{ 
    recog = j_recog_new(); 
    jconf = j_jconf_new(); 


    //Julius callback Functions 
    callback_add(recog, CALLBACK_EVENT_PROCESS_ONLINE, StartOnEngineStart, callback_ptr.get()); 

    callback_add(recog, CALLBACK_RESULT, StartOnRecognized, callback_ptr.get()); 

} 

The clr_scoped_ptr class is here.不會有太多的許可證要求,請務必遵循他們雖然如果你使用它。

+0

這是我的恐懼。我在C++中生鏽,現在我使用Java和C#。 你能幫我一個樣品嗎? –

+0

指向實例的指針不能解析? –

+0

你有沒有使用過活動,沒有財產? –