我正在开发一个涉及多个C ++程序的项目,每个程序都接受输入并生成输出。数据(数十到数百个字节,可能是JSON)基本上是在一个方向上流动(异步),并且程序需要位于LAN周围的不同Linux计算机上。
由于数据只在一个方向流动,我不相信我需要像HTTP那样的事务模型。我认为消息队列模型(fire and forget)最有意义,应该简化每个程序的逻辑。仅注意消息已成功添加到远程队列就足够了。
我正在寻找的是如何在C或C ++中实现此消息队列的建议。似乎POSIX和Boost消息队列仅限于一个主机,RabbitMQ似乎支持弱C / C ++,并且MQ4CPP似乎对业务支持不足-关键作用。我错了吗?那么Boost ASIO或ACE或自己编写套接字代码怎么样?我期待着你的建议。
答案 0 :(得分:11)
就简单消息支持而言,ZeroMQ is hard to beat。它可用于许多语言绑定,并支持从简单的发送和接收到发布/订阅,扇出甚至消息传递管道的所有内容。代码也很容易消化,并且可以很容易地在模式之间切换。
查看他们的Weather Update Server sample(20种奇怪的语言)显示创建发布/订阅设置是多么容易:
zmq::context_t context (1);
zmq::socket_t publisher (context, ZMQ_PUB);
publisher.bind("tcp://*:5556");
publisher.bind("ipc://weather.ipc");
while(1) {
// Send message to all subscribers
zmq::message_t message(20);
snprintf ((char *) message.data(), 20 ,
"%05d %d %d", zipcode, temperature, relhumidity);
publisher.send(message);
}
我在一些混合的C#和Python进程中使用它没有太多麻烦。
答案 1 :(得分:2)
就个人而言,如果我理解这个问题,我认为您应该使用较低级别的TCP连接。它拥有您想要的所有保证交付,并且具有相当不错的Berkley套接字API。 我发现如果你愿意实现一个非常简单的协议(例如,四字节NBO消息长度, n 字节的数据),你可以变得非常简单,非常可定制,而且非常简单。如果你使用它,你也(如上所述)获得了很好的C支持(这意味着C ++支持,尽管事情不在类和方法中)。套接字代码也非常简单,它们具有异步IO和Linux / UNIX / POSIX IO功能的标准异步标志(这是其他好处之一,如果你对POSIX编程有所了解,你基本上知道套接字API)
学习套接字API的最佳资源之一是:
man
,man
,man
,man
,man
, make
,man
,...)此外,为了使数据网络可发送,如果您的数据是JSON,您不必担心。因为JSON只是ASCII(或UTF-8),所以它可以通过网络原始发送,只有一个长度标题。除非你试图发送二进制复杂的东西,否则这应该是完美的(如果你需要复杂的二进制,要么看看序列化还是为很多Segmentation Fault
做准备)。
另外,如果你去套接字路径,你可能想要使用TCP。虽然UDP会为你提供单向方面,但是让它可靠的事实是将你自带的解决方案与Linux内核提供的顶级TCP相提并论,TCP是一个显而易见的选择。
答案 2 :(得分:2)
RabbitMQ只是AMQP的一个实现。您可能想要调查Apache Qpid或其他可能更友好的C / C ++变体。虽然我没有第一手经验,但我有一个libamqp的C语言。我不确切知道你的要求是什么,但正确实施的AMQP是工业强度,应该比你在短时间内手工制作的任何东西更快,更稳定。
答案 3 :(得分:1)
我正在为类似的应用程序使用Boost Serialization和套接字发送。您可以在此处找到序列化的示例:
http://code.google.com/p/cloudobserver/wiki/TutoriaslBoostSerialization
在此页面上:
http://www.boost.org/doc/libs/1_38_0/doc/html/boost_asio/examples.html
在序列化下,您将找到有关如何制作服务器和客户端的示例。在特定端口上创建一个服务器,您可以在多个可以与该端口通信的计算机上生成多个客户端。
使用boost序列化的缺点是,如果你有一个简单的序列化数据结构,它会有很大的开销,但它确实很容易。
答案 4 :(得分:1)
另一个建议是分布式框架OpenCL。文档The OpenCL C++ Wrapper for API提供了有关库的更多信息。特别是,API函数cl::CommandQueue
可能对在网络设置中的设备上创建队列感兴趣。
答案 5 :(得分:1)
另一种消息传递解决方案是ICE(http://www.zeroc.com/)。它是多平台,多语言的。它使用了更多的RPC方法。