- 博客(61)
- 收藏
- 关注
原创 IO多路复用:select、poll、epoll
1)调用 select 时会陷入内核,这时需要将参数中的 fd_set 从用户空间拷贝到内核空间,select 执行完后,还需要将 fd_set 从内核空间拷贝回用户空间,高并发场景下这样的拷贝会消耗极大资源;通过 I/O 多路复用,程序可以在一个线程中等待多个 I/O 操作完成,无需为每个 I/O 操作创建独立的线程或进程,从而高效地处理大量并发 I/O 请求。阻塞IO:阻塞 I/O 是指当一个 I/O 操作被请求时,调用该操作的线程或进程会一直等待,直到 I/O 操作完成后才继续执行。
2024-10-31 21:05:29
627
原创 设计模式:单例
3.使用static成员函数定义接口函数与实例指针保证唯一,使用互斥锁保证线程安全,使用智能指针避免内存泄漏。懒汉式:只有在类的实例被使用时才生成唯一实例。单例模式是一种设计模式,指在整个程序生命周期中有且仅有一个实例的类。可以分为懒汉式以及饿汉式。1.将构造函数设置为private,可以禁止栈上构造,避免生成多个实例。原理:当存在多线程申请实例时,局部静态变量只初始化一次是线程安全的。饿汉式:程序一旦开始运行就产生实例,自身没有线程安全问题。2.使用类静态变量返回实例引用(懒汉式推荐)
2024-10-09 17:23:51
527
原创 常见排序算法分析:堆排序
堆定义:堆是一种完全二叉树(叶子节点依次序排列,除去叶子节点为一个满树 ),其根节点为二叉树的最大值(大顶堆),或最小值(小顶堆)。每一层需要耗时O(1),因此实现这种插入策略的时间复杂度为O(height)= O(logn)(堆排序:堆排序利用堆的根节点为整个二叉树的最大值或者最小值的特性,循环堆化待排序序列,寻找每一次堆化后的最大值或者最小值与末尾元素进行交换从而达到排序的目的。时间复杂度为O(nlogn),空间复杂度根据具体实现如果采用非递归实现则为O(1),采用递归则跟递归栈深度有关。
2024-08-07 18:40:05
363
原创 自用:磁传感器数据解算
3字节数据的格式为有符号整型数,数据为补码格式,最高位为符号位。Kc为磁传感器的磁电系数Kc = 40nT/mV;其中:Vref为参考电压,本设备参考电压为2.5V;计算结果为负数时,说明磁场方向与参考方向相反。,所以它的实际值为它本身:6553026。,所以它的值为负数,实际值应为本身值减去。时为负数,实际值为本身值减去。即:14439602 -时为正数,实际值为本身;,小于8388607。,大于8388607。
2024-07-23 21:03:20
419
原创 OS:处理机进程调度
Note:进程的状态可以分为创建状态->就绪状态->运行状态->等待状态(IO或其他阻塞事务) 其实还有一个挂起状态,IO时切换至内核态等待完成事件,此时可以直接挂起进程,事件完成唤醒进程,执行其他用户指令。Round-Robin系统根据FCFS策略将所有就绪进程排列成一个就绪队列,设置一个时间片,时间到了产生一个中断,激活调度程序将CPU分给队首进程。创建状态 -> 就绪状态 -> 运行状态 -> 等待状态 -> 就绪状态 -> 运行状态 -> 挂起状态。主要考虑长作业进程跟短作业进程如何平衡资源分配。
2024-07-22 20:33:57
1110
1
原创 std::deque底层实现
每一个容器继承自己的base版本,base中储存重要的数据结构,deque主要由中控数组指针,中控数组大小以及首尾迭代器构成。这些元素放置在_Deque_impl<_Tp>类中,这个类公有继承allocator类型(实际上这样设计不好,不能说他的类型与allocator有关)。deque实际上表面是线性连续的,实质是分段的。主要通过迭代器模拟了连续容器的特点,对都是迭代器的功劳。迭代器元素如_Deque_iterator<_Tp>所示。主要保存元素分界,cur读写模拟头,以及指向中控数组的指针。
2024-07-19 11:02:57
227
原创 GCC bug looping runtime error AddressSanitizer:DEADLYSIGNAL? and then timing out.
执行sudo sysctl vm.mmap_rnd_bits=28解决。
2024-06-28 03:30:39
183
原创 Leetcode 矩阵问题
定义上下左右四个边界,在模拟的过程中更新边界即可。作为哈希set的优化可以使用多维数组存储已经遍历过的元素的数量,只要对应位置上的计数小于等于一则继续遍历,否则直接退出。本质是将遍历到的元素根据其值大小转换到一个对应的位置上,例如值为1,则将值为1的所有数据位置固定在0。解决此类问题最简单的想法就是使用哈希set,记录每行,每列,每个小九宫格已经出现的元素。Note:对于小九宫格的定位为题是一个常见的套路,因为9乘9矩阵被划分为3乘3的九宫格,所以可以使用[i / 3][j / 3]去定位九宫格。
2024-06-25 14:09:55
561
原创 cs144 LAB1 基于滑动窗口的碎片字节流重组器
可以定义装配器的窗口大小为capacity,范围为[_first_unassembled,_first_unassembled + _capacity]。每次计算缓冲区第一个期望字节序号,并保障每个字节碎片都在窗口范围内,这需要对碎片进行裁剪,裁剪过后的碎片可以直接加入缓存区。需要注意EOF这里有几个大坑,首先是EOF可能会提早到来,这时不能直接结束流写入需要进行判断。的总容量有固定的限制,多余的数据需要丢弃(此需要对端重传数据,这就引出了重传等知识点)2.判断碎片是否合法,不合法则直接丢弃。
2024-06-19 17:03:15
474
原创 Git 拉取指定分支 合并入主分支
如果在合并过程中出现冲突,Git会提示你哪些文件有冲突。你需要手动解决这些冲突。确保你已经安装了Git,并且已经克隆了自己的仓库到本地。是你想要合并的远程分支的名称。
2024-06-18 21:45:01
756
原创 Linux磁盘格式化与重新分区
3.sudo mkfs.ext4 /path 格式化磁盘。2.fdisk -l查看磁盘详细信息。1.df -BG查看磁盘挂载情况。4.挂载格式化后磁盘。
2024-06-16 14:13:02
583
原创 计算机网络(8) Finite State Machines(有限状态机)
主动关闭代表第一次主动发送FIN报文的一方的状态。发送SYN CLOSED >>>>>>>>>>>>>>SYN SENT(第一次握手)接收SYN发送SYN+ACK LISTEN>>>>>>>>>>>>>>>>SYN RECEIVED(第二次握手)调用Listen() CLOSE>>>>>>>>>>>>>>>>LISTEN。
2024-06-14 18:29:05
604
原创 计算机网络(7) 错误检测
接收方在接收到数据包后,会重新计算数据的校验和,并将这个校验和与接收到的校验和进行比较。:取反后,当接收方计算校验和时,将所有数据块、校验和以及取反结果相加,如果数据传输没有错误,总和应该为全1(即0xFFFF)。2. **求和**:将所有16位块的值求和,如果求和结果超过16位,则将高位的进位加回到结果中。2. **求和**:将所有块的值相加,如果超过16位,将进位部分加回到和中。3. **取反**:将最终的和取反,得到校验和。3. **取反**:将最终的和取反,得到校验和。
2024-06-14 15:51:52
1318
原创 计算机网络(6) ICMP协议
ICMP是网络通信中不可或缺的协议,虽然不传输用户数据,但在网络管理和诊断中起着重要作用。理解ICMP及其各种消息类型对于网络管理员和工程师来说是至关重要的,它有助于维护网络的正常运行和性能优化。
2024-06-14 13:37:46
925
原创 计算机网络(6) UDP协议
UDP协议因其简单、高效、低延迟的特点,在实时性要求高的应用场景中被广泛采用。然而,由于其不可靠传输的特性,在需要确保数据完整性和顺序的场景中,TCP则更为适用。UDP和TCP各有优劣,选择哪种协议取决于具体应用的需求。
2024-06-14 13:05:49
699
原创 计算机网络(5) ARP协议
下面是Wireshark抓的ARP请求报文,大家可以看到数据链路层的Ethernet Address of destination是全ff,说明这是一个广播包,是为了获取指定IP的MAC地址,可以看到ARP包中的Target IP address是192.168.0.7,但Target MAC address是全0,说明当前还不知道目标主机的MAC地址,Opcode为1,说明这是一个ARP请求报文。ARP协议的基本功能就是通过目标设备的IP地址,查询目标设备的MAC地址,以保证通信的进行。
2024-06-12 23:17:06
2446
原创 计算机网络(1) OSI七层模型与TCP/IP四层模型
TCP/IP 模型将 OSI 模型的应用层、表示层和会话层合并为应用层,将 数据链路层和物理层合并为网络接口层。应用层为用户提供的服务有文件传输服务、远程登录服务、电子邮件服务、打印服务、数据库服务等。,传输层为两台主机进程之间通信提供服务,处理数据包错误、数据包次序等关键传输问题。,物理层实现相邻节点间比特流的透明传输,尽可能屏蔽传输介质和通信手段的差异。,网络层选择合适的路由和交换结点,确保数据及时传送,主要包括IP协议。,表示层负责数据格式的转换,如加密解密、转换翻译、压缩解压缩等。
2024-06-11 20:56:30
969
原创 C++ Thread多线程并发记录(9)promise与future异步传值
promise承诺体负责储存一个“未来值”(常由其余线程传递)。一.std::promise。二.std::future。
2024-06-04 16:33:36
252
原创 C++ Thread多线程并发记录(8)生产者-消费者模型与信号量(条件变量)
举一个简单的例子,在网络通信过程中消费者可以是多个数据写入线程,负责向输入缓冲区写入以太网数据。需要注意,这里的生产者与消费者是两类线程,实现了数据收发与数据处理的解耦合。std::conditon_variable(c11)在头文件<condition_variable>定义,它是与std::mutex一起使用的同步原语。消费者线程在没有接到通知时,一直处在阻塞等待通知的状态,对比死循环加条件判断的形式更节省OS资源消耗。需注意,在通知前先释放锁,不然会出现子线程唤醒后再次阻塞的风险(假通知)。
2024-06-04 15:41:32
511
原创 c11 std::function通用多态函数包装器
或其他函数对象,以及成员函数指针和数据成员指针。的实例能存储、复制及调用任何。是一种通用多态函数包装器。——函数(通过其指针)、
2024-06-03 15:53:24
327
原创 C++ Thread多线程并发记录(7)模拟主线程与子线程通信简单示例
2.创建主线程消息发送处理类。3.实现建议的消息处理逻辑。1.创建线程启动停止基类。
2024-06-03 11:58:10
419
原创 C++ Thread多线程并发记录(6)std::lock std::scoped_lock解决死锁问题
假设有两个线程各自独立占有相同的两把锁,且两线程加锁顺序不一致。将会导致死锁发生,假如线程1先上锁A再上锁B,线程2先上锁B再上锁A,将有可能导致死锁。(死锁的发生是时间敏感的)。二.使用std::lock(c11)与std::scoped_lock(c17)解锁此类死锁。
2024-06-03 10:27:36
401
原创 C++ Thread多线程并发记录(4)互斥锁,递归锁,超时锁,共享锁
举个例子,一个递归函数,需要被一个线程多次调用,且当前函数中某些临界区需要加锁,如果我们使用常规的mutex等锁进行多次lock(),必然会导致程序异常,此时如果使用递归锁,那么将允许我们多次lock()。有些需要加锁的业务方法,在进行一些业务组合的时候,可能会被调用多次,如果使用常规锁,可能会死锁,比如上一次的加锁还没有解锁,第二次调用的地方又进行加锁,导致死锁,导致程序执行不下去。简单地说,递归锁是一种在锁已被持有的情况下,允许同一线程对该锁进行多次加锁的机制,也叫可重入锁。四.共享锁(读写锁)
2024-06-01 17:38:57
952
原创 C++ Thread多线程并发记录(2)同步操作
大多数情况下,也可以在函数调用之前向 std::async 传递一个额外参数,这个参数的类型是 std::launch ,还可以是 std::launch::defered ,表明函数调用延迟到wait()或get()函数调用时才执行,std::launch::async 表明函数必须在其所在的独立线程上执行, std::launch::deferred | std::launch::async 表明实现可以选择这两种方式的一种。同样,等待的线程会等待更长的时间,也会消耗更多的系统资源。
2024-05-28 18:43:39
679
原创 个人记录Boost.asio安装
连接远程编译环境开发的时候,clion里面,头文件突然就都标红了,但是能正常编译。出现这样的情况,原因是clion缓存的symbol以及头文件信息与远程的不一致。因此我们需要让clion重新从远程环境拉取就行。先查找boost库,再包含boost头文件路径,最后链接就可以。三.解决Clion远程开发第三方库飘红无提示问题。OS版本:ubuntu20.04。2.安装boost.asio。
2024-05-27 17:29:59
620
原创 C++ Thread多线程并发记录(1)线程间共享数据与互斥量
ppt来源https://www.bilibili.com/video/BV1Bw4m1R7MP?p=13&spm_id_from=pageDriver&vd_source=b9a49db2b7e1900aa29226c070f29e30
2024-05-27 16:28:17
990
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人