6

我正在使用一个具有如下回调的库:

void onReceive (Lacewing::Server &Server, Lacewing::Server::Client &Client,
                char * Data, int Size) {
  /* callback body */
}

Server.onReceive (onReceive); /* to register the handler */

我希望能够将其包装在一个类中,该类可以决定在收到数据包时要做什么(观察者模式)。

如何使用 C 风格的回调来做到这一点?该库没有定义要继承的接口。

谢谢

4

2 回答 2

2

由于您使用的是 liblacewing,因此每个类都有一个void * Tag为用户数据提供的成员:

/* class method */

void MyServer::onReceive (Lacewing::Server &Server, Lacewing::Server::Client &Client,
            char * Data, int Size)
{
     /* callback body - this is inside the class */
}


/* global function wraps the class method */

void onReceive (Lacewing::Server &Server, Lacewing::Server::Client &Client,
            char * Data, int Size)
{
    ((MyServer *) Server.Tag)->onReceive (Server, Client, Data, Size);
}

然后:

Server.Tag = myServerInstance; /* set the class instance pointer */
Server.onReceive (::onReceive); /* register the global function */
于 2012-05-26T20:01:41.370 回答
1

如果我理解正确,你可以用两种不同的方式来做。

假设此回调结构使用 Data 参数允许您将自己的数据传递给回调函数(常见范例),您可以这样做:

class MyProcessingClass
{
public:
    MyProcessingClass();
    virtual ~MyProcessingClass();

    // Do whatever processing in this method
    virtual void onReceive(Lacewing::Server &Server, Lacewing::Server::Client &Client);
}

void onReceive (Lacewing::Server &Server, Lacewing::Server::Client &Client,
                char * Data, int Size)
{
    if ( Data != NULL )
    {
        MyProcessingClass *handler = reinterpret_cast<MyProcessingClass *>(Data);
        handler->onReceive( Server, Client );
    }
}

或者,如果您需要处理数据指针而不是“用户数据指针”,那么您可能必须使用单例、某种全局变量或类似的东西。以我的经验,这是使用回调的一种不太常见的方式,希望这不是您要处理的。

MyProcessingClass g_Processor;

MyProcessingClass *GetProcessor()
{
    return &g_Processor; // or some other way of getting your instance
}

void onReceive (Lacewing::Server &Server, Lacewing::Server::Client &Client,
                char * Data, int Size)
{
    MyProcessingClass *handler = GetProcessor();
    if ( handler != NULL )
    {
        handler->onReceive( Server, Client );
    }
}
于 2012-05-13T23:33:17.957 回答