• 0MQ绑定Delphi版说明 标签: delphiDelphiDELPHIzeromqzeroMQZeroMQZMQzmq 20130220 20:19 13


    0MQ绑定Delphi版

    这是一份ZMQ绑定。测试环境Delphi7,BDS2006,FPC 2.6.0(目前仅Window)。

    概述

    程序包中含有一个dll的wrapper(zmq.pas),和一个高层API(zmqapi.pas)。

    它应该能够工作于 ZMQ 2.2.0,和 3.2.0rc1(实验性)。要使用 v3.2 的 dll,在zmq.inc中定义zmq3({$define zmq3})。dll来自于官方发行版

    使用

    你应该使用高层API,那会节省你大量时间,而且附带效果是代码也将更容易阅读。

    首先,你应该创建一个上下文

    context := TZMQContext.Create; 

    有很多种套接字类型,参见指南,每种都有一个常量。要创建例如一个REP套接字,这么写:

    socket := context.Socket( stRep );
    
    // 绑定套接字
    socket.bind( 'tcp://*:5555' );
    
    // 连接套接字
    socket.connect( 'tcp://localhost:5555' );
    
    

    API中有很多中方法来发送消息。你可以发送单份,或多份消息,阻塞或非阻塞(v3中称为dontwait不等待)模式。

    // 阻塞模式(默认)发送一个字符串就像这么简单:
    socket.send( 'Hello' );
    
    // 或者用非阻塞模式
    socket.send( 'Hello', [rsfNoBlock] );
    // 这种情况下如果消息无法入队则将抛出一个EZMQException异常,
    // 异常类型为EAGAIN。
    
    // 从stream发送数据(别忘了设置stream的位置到读取位置)
    socket.send( stream, size );
    
    // 发送多段消息。
    // 多个字符串:
    socket.send( ['Hello','World'] );
    
    // 这等同于:
    socket.send( 'Hello', [rsfSndMore] );
    socket.send( 'World' );
    
    // 或者使用TStrings。
    tsl := TStringList.Create;
    tsl.Add( 'Hello' );
    tsl.Add( 'World' );
    socket.send( tsl );
    tsl.Free;
    
    

    接收消息就像这么容易:

    msize := socket.recv( msg );
    // 新的消息到了msg中,而msize持有消息的长度
    
    // 到一个stream中
    msize := socket.recv( stream );
    
    // 读取多段消息
    tsl := TStringList.Create;
    mcount := socket.recv( tsl );
    // 这将会添加多个消息的部分到字符串列表,并返回接收的消息数量。
    
    

    CTRL+C的处理

    这是个小技巧。在Windows中信号处理与posix系统有所不同。阻塞调用不会接收到SIGINT,只会持续的阻塞。要克服这个问题,已安装的处理器终止了上下文,所以阻塞调用例如recvpoll,等等...将接收到ETERM。这仅在Windows。

    如果你将你的无限循环代码写为这样,你可以很干净的终止。

    while not context.Terminated do
    try
      socket.recv( msg );
    except
      // 处理异常,或者
      context.Terminate;
    end;
    
    context.Free;
    
    

    轮询

    轮询可以工作在两种不同方式,让我们称第一种为同步,第二种为异步方式。异步版本创建了一个线程,在其中做轮询。

    • 同步
    // 创建上下文
    context := TZMQContext.Create;
    socket := context.Socket( stDealer );
    socket.connect( address );
    
    // 创建轮询器。参数true告诉轮询器使用同步轮询
    poller := TZMQPoller.Create( true );
    
    // 注册套接字。
    poller.register( socket, [pePollIn] );
    
    timeout := 100; // 100ms
    while not context.Terminated do
    begin
      rc := poller.poll(timeout);
      if rc > 0 then
        do something...
    end;
    
    poller.Free;
    socket.Free;
    context.Free;
    
    
    • 异步方式

    这个实现使用了一种reactor模式,轮询器启动了一个新的线程,并在类和创建的线程之间创建了一对套接字连接。所以这个轮询器的实现不是线程安全的,不要在不同线程中去注册、反注册套接字。

    procedure TMyClass.pollerEvent( socket: TZMQSocket; event: TZMQPollEvents );
      begin
        do something...
      end;
    
    // 创建上下文。
    context := TZMQContext.Create;
    
    socket := context.Socket( stDealer );
    socket.connect( address );
    
    // 创建轮询器。第二个参数可以为nil,此时轮询器会创建自己的上下文。
    poller := TZMQPoller.Create( false, context );
    
    poller.onEvent := pollerEvent;
    
    // 注册套接字。如果第三个参数为true,注册将阻塞直到套接字注册完毕。
    poller.register( socket, [pePollIn], false );
    
    
    

    监视套接字(仅在v3.2可用)

    // 像这样定义一个回调
    procedure TMyClass.MonitorCallback( event: TZMQEvent );
    begin
      // do something.
    end;
    
    // 注册这个回调
    socket.RegisterMonitor( MonitorCallback, cZMQMonitorEventsAll );
    
    // MonitorCallback将会在由RegisterMonitor创建的分离的线程中被调用。
    
    // 你可以这么调用来反注册监视。
    socket.DeRegisterMonitor; 
    
    

    示例

    示例位于 zguide examples/Delphi 目录.

    变更

    • New poller class
    • poll function of TZMQPoller has a new optional parameter "pollCount".
    • Upgrade dll-s to v3.2.2 RC2
    • New monitoring logic implemented.
    • Default ZMQ version for the binding is now3.2 ( can switch back to 2.2 by not defining zmq3 in the zmq.inc file )

    作者

    以下为项目的贡献人员:

    	Balazs Varga <bb.varga@gmail.com> 
    	Stathis Gkotsis<stathis.gkotsis@gmail.com>
    	Stephane Carre <scarre.lu@gmail.com>
    

    版权

    遵循 GNU Lesser General Public License (LGPL) 条款将被授权自由使用此软件。细节请参看包含在发行内容中的文件COPYING.LESSER


  • 相关阅读:
    (转)如何最佳地使用memcached?
    win7 安装 memcached
    (转)怎么把主机的文件复制到虚拟机上
    memcache和redis本质区别在哪里?
    关于memcached
    (转)memcached注意事项
    (转)Memcached深度分析
    《项目架构那点儿事》——快速构建Junit用例
    《项目架构那点儿事》——工具类,你喜欢你就拿去
    《项目架构那点儿事》——Hibernate泛型Dao,让持久层简洁起来
  • 原文地址:https://www.cnblogs.com/zerofire/p/7162157.html
Copyright © 2020-2023  润新知