zoukankan      html  css  js  c++  java
  • select客户端模型封装——回调方式快速建立客户端

    SockClient.h

    #pragma once
    
    #include<functional>
    
    #define _WINDOWS
    #ifdef _WINDOWS
        #define _WINSOCK_DEPRECATED_NO_WARNINGS 
        #ifndef _WINSOCK2_H
            #include<WinSock2.h>
            #pragma comment(lib,"ws2_32.lib")
        #endif
        #ifndef _WINDOWS_H
            #include<Windows.h>
        #endif
    #endif
    
    class SocketClient
    {
    private :
        struct sockaddr_in ServerAddr;
        SOCKET s;
        bool stopFlag = false;
    
    public:
        SocketClient();
        ~SocketClient();
        int connectServer(char *addr,int port);
        int sendToServer(char *buf, int len);
        int recvFromServer(char *buf, int len);
        void startRecv(std::function<void ()> recvEvent,std::function<void()> breakEvent);
    };

    SocketClient.cpp

    #include "SocketClient.h"
    
    SocketClient::SocketClient()
    {
        WORD var = MAKEWORD(2, 2);
        WSADATA wsaData;
        WSAStartup(var, &wsaData);
    
        this->s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
        this->ServerAddr.sin_family = AF_INET;
    
    }
    
    
    SocketClient::~SocketClient()
    {
        closesocket(s);
        WSACleanup();
    }
    
    /*
    *
    *    连接到客户端
    *    成功返回0 失败返回-1    
    *
    */
    int SocketClient::connectServer(char * addr, int port)
    {
        this->ServerAddr.sin_port = htons(port);
        this->ServerAddr.sin_addr.S_un.S_addr = inet_addr(addr);
    
        int ret = connect(s, (const sockaddr*)&this->ServerAddr, sizeof(struct sockaddr_in));
    
        return ret;
    }
    
    int SocketClient::sendToServer(char * buf, int len)
    {
        return send(this->s, buf, len, 0);
    }
    
    int SocketClient::recvFromServer(char * buf, int len)
    {
        return recv(this->s, buf, len, 0);
    }
    
    void SocketClient::startRecv(std::function<void()> recvEvent, std::function<void()> breakEvent)
    {
        this->stopFlag = true;
        while (true)
        {
            if (stopFlag)break;
    
            fd_set readSet;
            FD_ZERO(&readSet);
            FD_SET(this->s, &readSet);
    
            int ret = select(this->s, &readSet, 0, 0, 0);
    
            if (ret < 0) {
                //Connect breaks
                breakEvent();
                break;
            }
            else if (ret == 0) {
                //No Message
                continue;
            }
            //Have Message
            if (FD_ISSET(&readSet, this->s))
            {
                FD_CLR(this->s, &readSet);
                recvEvent();
            }
        }
    }

    main.cpp

    #include <iostream>
    #include <cstring>
    #include <functional>
    
    #define _WINDOWS
    
    #include "SocketClient.h"
    
    using namespace std;
    
    char IP[] = "127.0.0.1";
    int Port = 2019;
    int abc;
    
    int main()
    {
        SocketClient *Client = new SocketClient();
        cout << "正在连接..." << endl;
        if (Client->connectServer(IP, Port) != 0)
        {
            cout<< "连接失败" <<endl;
            cin >> abc;
            return 0;
        }
        cout << "连接成功" << endl;
        Client->startRecv([Client]() -> void {
            char buf[1024];
            int n = Client->recvFromServer(buf, 1024);
            if (n > 0) {
                buf[n] = '';
                cout << "Recv: " << buf << endl;
            }
        }, []() -> void {
            cout << "Connect break;" << endl;
        });
        cin >> abc;
        return 0;
    }
  • 相关阅读:
    拟阵学习笔记
    HNOI 2016 解题报告
    HNOI 2015 解题报告
    一类动态规划问题状态的简化
    组合数学学习笔记
    简单多项式学习笔记
    基础线代学习笔记
    后缀数据结构学习笔记
    图论学习笔记
    AT3673 [ARC085D] NRE 题解
  • 原文地址:https://www.cnblogs.com/HadesBlog/p/11805381.html
Copyright © 2011-2022 走看看