Select模型设计200人服务器

来源:互联网 发布:python 捕捉ctrl c 编辑:程序博客网 时间:2024/06/08 15:45
/*
Select模型设计200人服务器

问题描述:
    利用select模型设计能够同时支持200人在线的服务器框架

核心难点:
    1. select模型缺省情况下最多能支持64人同时在线
    2. 如何精确控制在线人数不超过200人

解决思路:多线程处理:

    1. 主线程负责接收客户端连接

    2. 子线程负责与客户端进行通信,每个线程最多处理64个客户请求


数据维护:
    1. 主线程负责服务器逻辑控制,维护服务器数据对象,其具体实现见服务器对象类(CService设计)设计
    2. 每个子线程负责维护一个线程对象数据类型其类型,其具体类型见线程数据对象类(CThreadObj)设计

*/


主函数代码

#include "stdafx.h"#include "Service.h"#include "../InitSocket.h"CInitSocket g_InitLib;int main(){CService Serv(4567);Serv.RunServ();    return 0;}

服务器类设计


/*
CService对象设计
1. 数据对象
    1) 监听套接字
    2) 端口
    3) IP
    4) 线程对象列表

2. 数据处理方法
    1)服务器初始化(创建套接字,绑定套接字,监听套接字)
    2)运行服务器    
    (接收到客户连接,将通信套接字交给对应线程对象,
        如果线程对象没有启动,则启动对应的线程)
    - 成功接收连接
    - 是否有空余线程对象
        否 创建新的线程对象,加入列表,启动线程
        是 将套接字交给新的线程    
        - 线程是否启动    否 启动想成
                        是 next
*/

#include "ThreadObj.h"class CService{public:CService();CService(USHORT uPort, const char *pszIP = NULL);~CService();public://初始化服务器bool InitServ(USHORT uPort, const char *pszIP = NULL);//运行服务器bool RunServ();private://监听套接字SOCKET m_sListen;//服务器端口号USHORT m_uPort;//服务器IPULONG m_uIP;//服务器线程列表list<CThreadObj> m_ThreadList;};

线程对象设计

/*
线程对象类设计思路
1. 每个线程负责维护的数据对象
    1) 当前线程需要处理的socket集合
    2) 当前线程socket数量
    3) 当前系统socket总数
    4)    当前线程是够正在运行

2. 数据处理方法
    1) 套接字集合处理方法
        增,删,改,查,清空,
    2) 判断方法
        是否为空,是否已满,线程是否运行
    3)Get方法
        获取自身引用,获取线程socket总数,获取系统socket总数

3. 运算符重载
    1) [] 获取指定索引位置的socket集合对应的socket对象
    2) += 添加socket
    3) == 对象是否相等,对应的socket是否在集合中
    4) -= 移除对象

4. 构造函数
    缺省构造        需要
    类型转换构造    需要(SOCKET s)
    拷贝构造        不需要
    移动构造        不需要
    其他构造        不需要
*/

class CThreadObj{public:    CThreadObj();    ~CThreadObj();private:    // 当前线程套接字集合    fd_set m_fdCurThreadClient;    // 当前线程套接字总数    int m_CurThreadCount;    // 当前系统套接字总数    static int m_nSysTotal;    // 当前线程是否启动    bool m_bThreadRun;public:    // 向当前线程中添加套接字 s    bool AddSocket(SOCKET s);    //从当前线程中移除套接字 s    bool RemoveSocket(SOCKET s);    // 判断套接字是否在当前线程    bool IsSet(SOCKET s);    // 当前线程套接字是否为 0    bool IsEmpty();    // 当前系统套接字是否已满    bool IsFull();    // 当前线程是否正在运行    bool IsRun();    // 获取当前线程套接字数量    int GetCount();    //启动线程    bool RunThread();    //获取当前系统对象的引用    CThreadObj& GetThreadObj();    private:    // 清空当前线程中套接字,析构或者异常时候使用    bool Clear();    // 获取系统套接字总数    static int GetTotal();private:    // 线程过程函数    static DWORD  WorkItemFun(PVOID lParam);    };

具体实现见上传文件





原创粉丝点击