C++的简单异步

位置
主要有:懒/执行器/生成器/批操作/协程锁/协程条件变量/有栈协程等组件.

简单回声示例

简单异步::协程::<>
会话(传控::套接字 套接字){(;;){
        常 大小型 最大长度=1024;
        符 数据[最大长度];[错误,长度]=协待 异步读些(套接字,异网::缓冲(数据,最大长度));(错误){
            抛 异网::系统错误(错误);
        }
        协待 异步写(套接字,异网::缓冲(数据,长度));//两个协待.
    }
}

协程是特殊函数,C++20挂起协程纯数据处理.
用途:事件驱动应用/异步IO/生成器/惰性求值.

异步发送邮件的客户端

假如用回调,最简单基本上就是>4个圈.难以维护.用协程来写:

动 错误码=协待 异步连接(主机,端口);//连接
错误码=协待 异步处理握手();//握手
发送数据=构建请求();
错误码=协待 异步写(发送数据);//写(){
    协待 异步读(响应);//读数据(完成()){
        输出<<"发送电邮好\n";;
    }

    附加响应(接收数据_);
}

用协程改写异步代码,圈复杂度降低到2,即使后面再增加一些异步处理的业务逻辑,也不会能增加圈复杂度,始终保持逻辑的简单易懂,这就是协程在异步IO场景下的典型应用.

异步客户端示例

简单异步::协程::<>发送电邮(){
    串 主机=服务器_.服务器;
    大小型 位置=主机.("://");(位置!=::几位置)主机.擦除(0,位置+3);

    异网::ip::传控::解析器::查询 查询(
        主机,服务器_.端口,异网::ip::解析器查询基::数值服务);
    错误码 ec;
    动 端点步=解析器_.解析(查询,ec);

    ec=协待 异步连接(io环境_,套接字_,主机,服务器_.端口);//连接(ec){
        输出<<"连接错误:"<<ec.消息()<<'\n';
        抛 异网::系统错误(ec);
    }

    输出<<"连接好\n";
    如 常式(是安套层)升级至安套层();

    构建请求();
    常 符*=异网::转换缓冲<常 符*>(请求_.数据());
    输出<<<<'\n';
    [[也许未用]][写错码,大小]=协待 异步写(
        取套接字(),异网::缓冲(,请求_.大小()));//异步写.(写错码){
        输出<<"写失败,原因:"<<ec.消息()<<'\n';
        抛 异网::系统错误(写错码);
    }(){
        常 整 最大长度=1024;
        符 读缓冲[最大长度];
        [[也许未用]][读错码,大小]=协待 异步读些(
            取套接字(),异网::缓冲(读缓冲,最大长度));//异步读(读错码){
            输出<<"读失败,原因:"<<ec.消息()<<'\n';
            抛 异网::系统错误(读错码);
        }

        串视 内容(读缓冲,大小);
        输出<<内容;(内容.("250邮件好")!=串视::几位置){
            输出<<"结束简邮\n";;
        }
    }
}

就像写同步代码一样写异步代码,发送邮件的核心函数异常处理和日志输出也不过50行代码,代码简洁易懂,再也不用回调函数了.这就是async_simple协程库的威力!

posted @ 2022-03-15 13:04  zjh6  阅读(31)  评论(0)    收藏  举报  来源