基于多反应堆的高并发服务器【C/C++/Reactor】(中)ChannelMap 模块的实现
(三)ChannelMap 模块的实现
这个模块其实就是为Channel来服务的,前面讲了Channel这个结构体里边它封装了文件描述符。假如说我们得到了某一个文件描述符,需要基于这个文件描述符进行它对应的事件处理,那怎么办呢?我们就需要找到文件描述符对应的那个Channel,因为在这个Channel里边有事件对应的回调函数,只有找到Channel之后,我们才能够知道当读事件被触发了,或者说写事件被触发了。咱们调用的函数是什么呢?在C语言里,没有stl容器的,那如何实现一个对应关系呢?最简单的方式就是使用数组。有一种查找效率更高的数据结构就是哈希,其实它就是通过数组来实现的。通过空间换时间,牺牲一部分内存空间换取数据的读取效率。看下图,对于每个数组来说,都有一个唯一的下标,是从零开始的,对于文件描述符来说,最小值也是零,所以我们可以让数组的下标去对应文件描述符,0号下标对应0号文件描述符,1号下标对应1号文件描述符。假设说和客户端建立了一个连接,得到了5号文件描述符,那么前边的这些文件描述符是不是有可能是空的?也就是说下标对应的值是空的,这个有关系吗?没关系啊,因为前边说的咱们实现的这种map,主要的思路是空间换时间,所以要换取效率,必然是要牺牲一部分空间的。使用了这种方式,就直接能够通过下标来取出对应的值,不需要遍历。

主要介绍了ChannelMap的实现思路,包括使用数组和哈希等数据结构,以及如何通过空间换时间来提高查找效率。同时,还介绍了如何定义map对应的那个结构体,以及如何实例化这个数组。
核心观点:
- 使用数组或哈希等数据结构实现ChannelMap,以提高查找效率。
- 通过空间换时间的思想,牺牲一部分空间来换取效率。
- 在map对应的结构体中,主要的数据成员是一个数组,数组的大小需要根据实际情况确定。
- 需要实例化数组,并确定数组中存储的指针类型。
ChannelMap相关函数
(1) channelMapInit
功能:为ChannelMap分配内存
- 分配内存给指针。
- 计算内存大小:size * 指针的字节数(指针为4字节)。
- 将map指针的地址返回给调用者。
(2) ChannelMapClear
功能:清空ChannelMap结构体。
- 判断map是否为空。
- 遍历数组,释放指针指向的内存(如果指针不为空)。
- 释放数组指向的内存。
- 将数组的size置为0。
注意事项:内存释放分为两部分,数组元素指向的内存和数组本身指向的内存。
(3) makeMapRoom 数组扩容函数
功能:判断并扩容ChannelMap中的list。
- 判断当前list的size是否大于newSize。
- 如果需要扩容,调用realloc函数重新分配更大的内存给list。
注意事项:只有当map中的size小于newSize时才需要进行扩容操作。
- Channel.h
#pragma once
#include "Channel.h"
struct ChannelMap {struct Channel** list;int size;// 记录指针指向的数组的元素总个数
};// 初始化
struct ChannelMap* channelMapInit(int size);// 清空map
void ChannelMapClear(struct ChannelMap* map);// 重新分配内存空间
bool makeMapRoom(struct ChannelMap* map,int newSize,int unitSize);
- Channel.c
#include "ChannelMap.h"
#include <stdio.h>
#include <stdlib.h>
struct ChannelMap* channelMapInit(int size) {struct ChannelMap* map = malloc(sizeof(struct ChannelMap));map->size = size;map->list = (struct Channel**)malloc(sizeof(struct Channel*) * size);return map;
}void ChannelMapClear(struct ChannelMap* map) {if(map != NULL) {for(int i=0;i<map->size;++i) {if(map->list[i] != NULL) {free(map->list[i]);}}free(map->list);map->list = NULL;}map->size=0;
}bool makeMapRoom(struct ChannelMap* map,int newSize,int unitSize) {if(map->size < newSize) {int curSize = map->size;// 容量每次扩大原来的一倍while(curSize < newSize) {curSize*=2;}// 扩容 reallocstruct Channel** temp = realloc(map->list,curSize * unitSize);if(temp == NULL) {return false;}map->list = temp;memset(&map->list[map->size],0,(curSize - map->size) * unitSize);map->size = curSize;}return true;
}
第一个精彩片段:channelMapInit函数的实现,详细介绍了如何为ChannelMap分配内存,包括计算内存大小和返回map指针的地址。对于理解ChannelMap如何创建和初始化非常重要,有助于理解后续的函数如何工作。
第二个精彩片段:ChannelMapClear函数的实现,详细介绍了如何清空ChannelMap结构体,包括释放内存和重置size。 这个片段对于理解如何管理和释放内存资源非常重要,有助于避免内存泄漏和其他相关问题。
内容概要:详细介绍了三个函数:channelMapInit、ChannelMapClear和makeMapRoom 对数组扩容函数的实现。这三个函数用于创建、初始化、清空和释放ChannelMap的内存,以及在必要时扩容数组。
核心观点:
- channelMapInit函数主要负责为ChannelMap分配内存,包括为指针成员分配内存,并根据元素个数和指针的字节数计算内存大小。
- ChannelMapClear函数用于清空ChannelMap结构体,包括释放数组元素指向的内存和数组本身指向的内存,并将数组的size置为0。
- 对数组扩容函数需要判断当前数组的size是否小于newSize,如果需要扩容,则调用realloc函数重新分配更大的内存给数组。
相关文章:
基于多反应堆的高并发服务器【C/C++/Reactor】(中)ChannelMap 模块的实现
(三)ChannelMap 模块的实现 这个模块其实就是为Channel来服务的,前面讲了Channel这个结构体里边它封装了文件描述符。假如说我们得到了某一个文件描述符,需要基于这个文件描述符进行它对应的事件处理,那怎么办呢&…...
微信小程序实现一个音乐播放器的功能
微信小程序实现一个音乐播放器的功能 要求代码实现wxml 文件wxss 文件js文件 解析 要求 1.页面包含一个音乐列表,点击列表中的音乐可以播放对应的音乐。 2.播放中的音乐在列表中有标识,并且可以暂停或继续播放。 3.显示当前音乐的播放进度和总时长&#…...
算法基础之表达整数的奇怪方式
表达整数的奇怪方式 中国剩余定理: 求M 所有m之积 然后Mi M / mi x 如下图 满足要求 扩展中国剩余定理 找到x **使得x mod mi ai**成立 对于每两个式子 都可以推出①式 即 用扩展欧几里得算法 可以算出k1,-k2和m2–m1 判无解 : 若**(m2–m1) % d ! 0** 说明该等式无解 …...
WEB 3D技术 three.js 设置图像随窗口大小变化而变化
本文 我们来讲讲我们图层适应窗口变化的效果 可能这样说有点笼统 那么 自适应应该大家更熟悉 就是 当我们窗口发生变化说 做一些界面调整比例 例如 我们这样一个i项目界面 我们打开 F12 明显有一部分被挡住了 那么 我们可以刷新 这样是正常了 但是 我们将F12关掉 给F12的…...
实战案例:缓存不一致问题的解决(redis+本地缓存caffine)
一.问题引入 目前在写项目的时候,在B端查看文章,A端修改文章。为了增加效率,以及防止堆内存溢出,在B端选择本地缓存文章的方案。但是目前出现了A端对文章修改之后,B端读的还是旧数据,出现了缓存不一致的问…...
【开源CDP】市场增长未来的探索,开源CDP带来的技术崛起与变革
数字化趋势之下,数据成了企业竞争的核心资源,不管是公域还是私域,网络俨然成了品牌打响市场的一线战场,然而,在这场数字战役里,许多企业不得不面临一个共同问题:数据零散、分散、平台众多、无法…...
第11章 GUI Page423~424 步骤六 支持文字,使用菜单,对话框输入文字
运行效果: 点击OK,然后再窗口上按住左键,拖动鼠标 关键代码: 新增头文件和成员,新增私有成员_text 成员初始化 为菜单项MenuItemText添加响应函数 新增创建TextItem()的代码...
【Qt】Qt Creator 警告: Unused parameter ‘xxx‘
1. 问题 Qt开发中,有些函数参数没有使用,会报Unused parameter xxx警告,这个警告不影响代码正常运行。 2. 屏蔽这个警告的方法 2.1 方法1 函数中添加 Q_UNUSED(arg); TestClass::TestClass(QObject *parent) {Q_UNUSED(parent); }2.2 方…...
「Vue3面试系列」Vue3.0性能提升主要是通过哪几方面体现的?
文章目录 一、编译阶段diff算法优化静态提升事件监听缓存SSR优化 二、源码体积三、响应式系统参考文献 一、编译阶段 回顾Vue2,我们知道每个组件实例都对应一个 watcher 实例,它会在组件渲染的过程中把用到的数据property记录为依赖,当依赖发…...
网络结构模式
一、C/S结构 服务器 - 客户机,即 Client - Server ( C/S )结构。 C/S 结构通常采取两层结构。服务器负责数据的 管理,客户机负责完成与用户的交互任务。客户机是因特网上访问别人信息的机器,服务器则是提 供信息供人…...
IIC及OLED实验
I2C (Inter-Integrated Circuit): I2C 是一种用于在芯片之间进行短距离数字通信的串行通信协议。它允许多个设备通过两根导线(一根数据线 SDA 和一根时钟线 SCL)进行通信。I2C 常常用于嵌入式系统中连接传感器、存储器、显示屏和其他外设。 数据线和时钟…...
day6 力扣公共前缀--go实现---对字符串的一些思考
今日份知识: curl -x 指定方法名 请求的url -d 请求体body里面的内容 //curl命令 curl -x Get 127.0.0.1:8080/add/user -d jinlicurl如果不指定方法,默认使用get方法,在go里面,get方法到底可以不可以把内容数据写在body里面传…...
27.Java程序设计-基于Springboot的在线考试系统小程序设计与实现
1. 引言 随着数字化教育的发展,在线考试系统成为教育领域的一项重要工具。本论文旨在介绍一个基于Spring Boot框架的在线考试系统小程序的设计与实现。在线考试系统的开发旨在提高考试的效率,简化管理流程,并提供更好的用户体验。 2. 系统设…...
Redis可视化工具Redis Desktop Manager mac功能特色
Redis Desktop Manager mac是一款非常实用的Redis可视化工具。RDM支持SSL / TLS加密,SSH隧道,基于SSH隧道的TLS,为您提供了一个易于使用的GUI,可以访问您的Redis数据库并执行一些基本操作:将键视为树,CRUD键…...
【C++】揭开运算符重载的神秘面纱
目录 一、引言 优点 二、介绍 1.定义 2.语法 三、示例 1.加法运算符重载 2.一元运算符重载 3.友元函数 4.流插入和流提取 5.自增自减运算符 总结 一、引言 何为运算符重载?运算符重载,是C中的一项强大特性,赋予了程序员在自定义类…...
竞赛保研 基于LSTM的天气预测 - 时间序列预测
0 前言 🔥 优质竞赛项目系列,今天要分享的是 机器学习大数据分析项目 该项目较为新颖,适合作为竞赛课题方向,学长非常推荐! 🧿 更多资料, 项目分享: https://gitee.com/dancheng-senior/po…...
前端常用的开发工具
前端常用的开发工具🔖 文章目录 前端常用的开发工具🔖1. Snipaste--截图工具2. ScreenToGif--gif图片录制3. Typora--Markdown编辑器4. notepad--文本代码编辑器5. uTools--多功能工具6. EV录屏--录屏软件7. Xmind--思维导图8. Apifox -- 接口调试9. Tor…...
鸿蒙开发语言介绍--ArkTS
1.编程语言介绍 ArkTS是HarmonyOS主力应用开发语言。它在TypeScript (简称TS)的基础上,匹配ArkUI框架,扩展了声明式UI、状态管理等相应的能力,让开发者以更简洁、更自然的方式开发跨端应用。 2.TypeScript简介 自行补充TypeScript知识吧。h…...
关于“Python”的核心知识点整理大全36
目录 13.4.4 向下移动外星人群并改变移动方向 game_functions.py alien_invasion.py 13.5 射杀外星人 13.5.1 检测子弹与外星人的碰撞 game_functions.py alien_invasion.py 13.5.2 为测试创建大子弹 13.5.3 生成新的外星人群 game_functions.py alien_invasion.py …...
安装nodejs,配置环境变量并将npm设置淘宝镜像源
安装nodejs并将npm设置淘宝镜像源 1. 下载nodejs 个人不喜欢安装包,所以是下载zip包的方式。这里我下载的node 14解压包版本 下载地址如下:https://nodejs.org/dist/v14.15.1/node-v14.15.1-win-x64.zip 想要其他版本的小伙伴去https://nodejs.org/di…...
Golang dig框架与GraphQL的完美结合
将 Go 的 Dig 依赖注入框架与 GraphQL 结合使用,可以显著提升应用程序的可维护性、可测试性以及灵活性。 Dig 是一个强大的依赖注入容器,能够帮助开发者更好地管理复杂的依赖关系,而 GraphQL 则是一种用于 API 的查询语言,能够提…...
智能在线客服平台:数字化时代企业连接用户的 AI 中枢
随着互联网技术的飞速发展,消费者期望能够随时随地与企业进行交流。在线客服平台作为连接企业与客户的重要桥梁,不仅优化了客户体验,还提升了企业的服务效率和市场竞争力。本文将探讨在线客服平台的重要性、技术进展、实际应用,并…...
Python爬虫(二):爬虫完整流程
爬虫完整流程详解(7大核心步骤实战技巧) 一、爬虫完整工作流程 以下是爬虫开发的完整流程,我将结合具体技术点和实战经验展开说明: 1. 目标分析与前期准备 网站技术分析: 使用浏览器开发者工具(F12&…...
【数据分析】R版IntelliGenes用于生物标志物发现的可解释机器学习
禁止商业或二改转载,仅供自学使用,侵权必究,如需截取部分内容请后台联系作者! 文章目录 介绍流程步骤1. 输入数据2. 特征选择3. 模型训练4. I-Genes 评分计算5. 输出结果 IntelliGenesR 安装包1. 特征选择2. 模型训练和评估3. I-Genes 评分计…...
android13 app的触摸问题定位分析流程
一、知识点 一般来说,触摸问题都是app层面出问题,我们可以在ViewRootImpl.java添加log的方式定位;如果是touchableRegion的计算问题,就会相对比较麻烦了,需要通过adb shell dumpsys input > input.log指令,且通过打印堆栈的方式,逐步定位问题,并找到修改方案。 问题…...
解决:Android studio 编译后报错\app\src\main\cpp\CMakeLists.txt‘ to exist
现象: android studio报错: [CXX1409] D:\GitLab\xxxxx\app.cxx\Debug\3f3w4y1i\arm64-v8a\android_gradle_build.json : expected buildFiles file ‘D:\GitLab\xxxxx\app\src\main\cpp\CMakeLists.txt’ to exist 解决: 不要动CMakeLists.…...
C语言中提供的第三方库之哈希表实现
一. 简介 前面一篇文章简单学习了C语言中第三方库(uthash库)提供对哈希表的操作,文章如下: C语言中提供的第三方库uthash常用接口-CSDN博客 本文简单学习一下第三方库 uthash库对哈希表的操作。 二. uthash库哈希表操作示例 u…...
Python 训练营打卡 Day 47
注意力热力图可视化 在day 46代码的基础上,对比不同卷积层热力图可视化的结果 import torch import torch.nn as nn import torch.optim as optim from torchvision import datasets, transforms from torch.utils.data import DataLoader import matplotlib.pypl…...
阿里云Ubuntu 22.04 64位搭建Flask流程(亲测)
cd /home 进入home盘 安装虚拟环境: 1、安装virtualenv pip install virtualenv 2.创建新的虚拟环境: virtualenv myenv 3、激活虚拟环境(激活环境可以在当前环境下安装包) source myenv/bin/activate 此时,终端…...
向量几何的二元性:叉乘模长与内积投影的深层联系
在数学与物理的空间世界中,向量运算构成了理解几何结构的基石。叉乘(外积)与点积(内积)作为向量代数的两大支柱,表面上呈现出截然不同的几何意义与代数形式,却在深层次上揭示了向量间相互作用的…...
