2017-05-25 146 views
0

方法「DataOperation」必須返回DataResponse類型中的值。返回類型的回調函數

我在我的異步請求回覆「LoadDataReply」裏面有一個回調函數,在這個回調函數中,我在收到的回覆中應用了一些業務邏輯並返回主方法(我不確定返回回調是否正確)。

你們可以幫我介紹如何爲LoadData方法的調用者返回值。

DataResponse DataOperation::LoadData(const RequestType request) 
{ 
DataResponse dataResponse; 
messageAssistant.AsyncRequest("LoadDataList", request) 
    .OnReply<MyResponseType>("LoadDataListReply", [this, &dataResponse](auto& reply) { dataResponse = this->LoadDataFromResponse(reply); }); 

return dataResponse; 
} 

DataResponse DataOperation::LoadDataFromResponse(const MyResponseType& reply) 
{ 
    ///Doing some operation with reply data 
    DataResponse dataResponse; 
    dataResponse.Data = reply.Data(); 
    return dataResponse; 
} 

上面的代碼沒有編譯。

我收到編譯錯誤,

error C4716: 'DataOperation::LoadData': must return a value 

注: -我已經更新了我的代碼,並編譯沒有任何問題。但是,我從LoadData返回的dataResponse對象最終沒有在LoadDataFromResponse中更新值。它具有初始值。

我怎樣才能確保它返回更新後的值而不是初始值?

+0

你不會在那裏返回任何價值? –

+0

我需要將dataResponse返回給LoadData方法的調用方。 – Joe

+1

@Joe那麼,'返回'呢? 'LoadData'是非void函數,但它沒有'return'語句,這反過來就意味着這樣的程序的行爲是不確定的。 –

回答

0

這已通過回調修復。

0

使用處理程序。你可以創建Handler(每個線程可以訪問的消息列表)。看看pseodocode下面:

class Handler { 
public: 
    Handler(); 
    // Constructor 
    ~Handler(); 
    // Destructor 
    void pushmessage (DataResponse* p); 
    DataResponse* popmessage(); 
    bool empty(); 
protected: 
    vector<DataResponse*> pool; 
    RTTICriticalSection CS; 
}; 

Handler::Handler() 
{ 
    CS = CreateCriticalSection; 
} 

Handler::~Handler() 
{ 
    DeleteCriticalSection(CS); 
} 

void Handler::pushmessage (DataResponse* p) 
{ 
    EnterCriticalSection(CS); 
    try { 
    pool.push_back(p) 
    } catch(...){ 
    // 
    } 
    LeaveCriticalSection(CS); 
} 

DataResponse* Handler::popmessage() { 
    DataResponse* dr = null; 
    EnterCriticalSection(CS); 
    try { 
    dr = pool.back(); 
    pool.pop_back(); 
    } catch(...){ 
    // 
    } 
    LeaveCriticalSection(CS);  
    return dr; 
} 

bool Handler::empty() { 
    bool res = true; 
    EnterCriticalSection(CS); 
    try { 
    res = pool.empty(); 
    } catch(...){ 
    // 
    } 
    LeaveCriticalSection(CS);  
    return res;  
} 

DataResponse DataOperation::LoadData(const RequestType request) 
{ 
    messageAssistant.AsyncRequest("LoadDataList", request) 
    .OnReply<MyResponseType>("LoadDataListReply", [this](auto& reply) { this->LoadDataFromResponse(reply); }); 
} 

/*DataResponse* */ void DataOperation::LoadDataFromResponse(const MyResponseType& reply) 
{ 
    ///Doing some operation with reply data 
    DataResponse* dataResponse = new DataResponse(); 
    dataResponse.Data = reply.Data(); 
    handler.pushmessage(dataResponse); 
    //return dataResponse; 
} 

//call this sub somewhere inside the idle cycle synchronized with the main thread 
void proceedMessages() { 
    while (!handler.empty()) 
    { 
    DataResponse* dr = handler.popmessage(); 
    //do something with dr 
    //free dr 
    } 
}