自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(28)
  • 收藏
  • 关注

原创 Linux锁的使用

一个函数在重入的情况下,运行结果不会出现任何不同或者任何问题,则该函数被称为可重入函数,否则,是不可重入函数。多线程会共享例如全局变量等资源,我们把会被多个执行流访问的资源称为临界资源,我们是通过代码访问临界资源的,而我们访问临界资源的那部分代码称为临界区。3.如果将对临界资源的访问加上锁,则这个函数是线程安全的,但如果这个重入函数若锁还未释放则会产生 死锁,因此是不可重入的。答案是会的,当一个线程申请完一个锁,访问完临界资源后,接下来该释放锁了,但是代码却写成了加锁,这就会导致死锁问题。

2024-04-08 19:44:44 880

原创 Linux内存管理以及页表如何寻址

如果要扩大文件缓冲区,无非就是在内存中再申请一个数据块,把文件某部分内容加载到这个数据块中,再把数据块添加到文件缓冲区里。由于文件系统IO的基本单位大小是4KB,所以我们的可执行程序被划分为一块一块的4KB大小,分块被加载到内存,所以内存也要划分为一块一块的4KB空间。4GB的内存中有1048576个页框(4GB),OS怎么知道哪个页框已经使用、哪个还没使用、哪个正在刷新、是否需要释放?我们把IO的4KB大小称为page size,把可执行程序的一块4KB称为页帧,把内存中的一块4KB称为页框。

2024-04-07 14:29:06 276

原创 Linux线程实现方案

线程并不是越多效率越高,对于计算密集型,假设计算机有两个八核CPU,最好创建16个线程并发执行,如果只有一个单核CPU,一个线程的效率是最高的,因为多个线程还要切换上下文资源,降低效率。所以每个新线程的栈在库中维护,动态库一般被加载到共享区中,当我们创建一个线程时,pthread库在堆中new一段空间,把堆空间的地址写到库里面,在库里面用指针维护它,在线程运行用到的一些栈空间通过这个指针就可以找到了。线程间切换的时候,地址空间和页表这些是不用切换的,只需要切换一些运行中产生的临时数据相关的寄存器。

2024-04-07 14:25:30 788

原创 进程地址空间

当执行代码的时候,读取访问到一个虚拟地址,查页表发现对应的内存和代码都没有,此时OS会暂停访问请求,接着在内存中开辟空间,把可执行程序需要执行的对应虚拟地址的代码加载到内存里,把对应的物理地址填充到页表中,把标志位该为11,最后让暂停的代码继续访问。若子进程先进行修改就把子进程的页表映射关系修改为新的物理地址,此时子进程指向新的空间并修改新空间的数据。哪个进程先改,哪个进程修改页表。,当子进程想要修改共同指向的数据时,OS会现在物理内存中开辟一块空间,并把原来空间的值拷贝一份,这块空间有新的物理地址。

2024-03-25 15:50:19 346

原创 命令行参数与环境变量

实际上,在Linux中大部分的命令是在磁盘当中真正存在的,需要fork创建子进程来执行命令,但还有一种命令,不需要子进程,有bash自己进行执行,这种命令等同于bash内部的一个函数,这种命令我们称之为内建命令。执行shell自带的指令时,会有一个默认搜索路径,称为环境变量PATH,在这里可以找到指令。export命令也是内建命令,因为export不能创建子进程,如果创建子进程会导致把环境变量导入到子进程的环境变量中。系统中会存在大量的环境变量,每一个环境变量都有它自己的特殊用途,用来完成特定的系统功能。

2024-03-24 10:39:55 481

原创 进程O(1)调度算法

一共140个优先级,一共140个进程队列,为了提高查找非空队列的效率,就可以用5*32个 比特位表示队列是否为空,这样,便可以大大提高查找效率。图中框起来的queue[140]代表着140个进程队列,其中下标为[0,99]为实时进程队列,[100,139]为普通进程队列。实时优先级,在运行队列中加入一个进程,这个进程必须一直运行到结束,一次调度运行完毕,适合需要快速响应的场景。3.当活动队列的进程时间片跑完后,与过期队列交换内容,获得一批新的活动进程。2.过期队列上放置的进程,都是时间片耗尽的进程。

2024-03-23 14:31:20 338

原创 Linux进程优先级

进程排队的本质就是确定优先级优先级是什么?得到某种资源的先后顺序。为什么要有优先级这个概念?本质上是因为资源不足。ps -l查看进程更详细的属性。Linux支持动态优先级调整,但不能直接修改PRI,要修改NI(nice值)间接修改PRI。

2024-03-23 09:38:57 252

原创 Linux进程的状态

进程状态在PCB里面也就是一个整型变量,int status。状态变化本质上是:(1)修改pcb中status的值(2)将pcb链入不同的队列中。

2024-03-22 22:17:19 247

原创 Linux进程简单介绍

我们可以同时启动多个进程,所以内存中一定会加载多个程序,有多个程序,操作系统就要把它们管理起来。首先要有一个struct结构体,里面要存储进程的属性等(这就是描述),再通过链表将多个PCB组织管理起来(这是组织)。如果某个进程想退出,操作系统可以通过PCB找到可执行程序的代码和数据并释放掉,再把进程的PCB从链表中删掉,操作系统就不再管理这个进程了。CPU在执行进程时,并不直接访问可执行程序,而是找到对应进程的PCB,根据PCB找到可执行程序的代码和数据,交给CPU。进程是运行起来的程序?

2024-03-22 09:07:48 197

原创 排序总结样例

一般的快排遇到大量重复元素会有所下降,若全部为同一个数,时间复杂度为O(N^2),使用三路归并进行优化,则可以很好解决这种问题,若所有元素相同,时间复杂度为O(N^2)。再取nums中随机一个数作为key,可以使排序时间复杂度更接近O(NlogN)

2024-01-06 21:07:42 364

原创 通过指针修改const常量问题

由于a被const修饰,则a已经是一个常量了,编译器在编译代码时,当遇到获取常量中的内容时,会直接使用常量中的内容替换该常量。a是常量,自己不能修改自己,但可以通过指针对a所在的空间进行修改,a的空间中存储的值也确实被改为了20。所以输出时,a已经被早先的10替换了,最终输出a = 10,*p = 20。程序运行结果为a = 10,*p = 20。

2024-01-06 09:34:26 404

原创 在Windows 32位操作系统中,假设字节对齐为4,对于一个空的类A,sizeof(A)的值为()?

在Windows 32位操作系统中,假设字节对齐为4,对于一个空的类A,sizeof(A)的值为()?三者会落在同一地址处,导致无法区分a123。假设空类大小为0,有a1,a2,a3。在主流编译器中空类大小设置为1。

2024-01-06 08:58:09 325

原创 在C++中,为了让某个类只能通过new来创建(即如果直接创建对象,编译器将报错),应该()

B、将析构函数设为私有,直接创建对象会报错,因为最终程序结束前要调用析构函数释放对象。而通过new来创建对象不会报错,虽然析构函数是私有的,但实际对象是存储在类指针类型中的,程序结束时销毁指针的空间不会调用类的析构函数,自然不会报错。在C++中,为了让某个类只能通过new来创建(即如果直接创建对象,编译器将报错),应该() A. 将构造函数设为私有。A、若将构造函数设为私有,则直接创建对象与通过new来创建都不可行,两者都要调用构造函数。C. 将构造函数和析构函数均设为私有。B. 将析构函数设为私有。

2024-01-05 12:19:50 438

原创 类中static成员相关问题

2.不能在类内初始化(类内只是声明),只能在类外初始化(类外进行定义,初始化时省略static关键字, 通过类型 类名。4.静态成员同样受private,public,protected访问限定符的限制。1.静态成员为所有对象所共享,不独属于某个具体对象,存放在静态区。如果在静态成员前加const进行修饰,则可以在类内进行初始化。5.静态成员函数没有this指针不能访问任何非静态成员。

2024-01-05 11:54:35 412

原创 指针类型数据在构造函数中的初始化问题

构造函数中,在没有指定值的情况下,指针要手动初始化为nullptr,否则指针的值不为空

2024-01-05 09:49:30 382

原创 C++中的static静态成员

2.静态成员函数不能访问或调用任何非静态成员和非静态成员函数,因为静态成员函数没有隐含的this指针。4.静态成员也是类的成员,同样受private,public,protected访问限定符的限制。1.静态成员不属于某个具体的对象,一个类的所有对象共同使用一个静态成员,静态成员存放在静态区。2.静态成员变量必须在类外定义,定义时不再加static,类中的只是声明。类中用static声明的成员为类的静态成员,静态成员在类外进行初始化。5.非静态成员函数可以调用类的静态成员函数。

2023-08-01 12:34:10 48 1

原创 赋值运算符重载详解及注意事项

编译器默认生成的赋值运算符重载已经可以解决问题了,为什么还要自定义呢?因为没有显示赋值运算符重载的话,编译器会生成默认赋值运算符重载,此时再定义一个全局赋值运算符重载会冲突。1.2 返回值类型:T&,返回引用可以提高返回的效率,有返回值目的是为了支持连续赋值。自定义实现赋值运算符重载进行深拷贝以解决两个_array指向同一块空间的问题。如果类中未涉及到资源管理,赋值运算符是否实现都可以;内置类型是直接赋值的,自定义类型需要调用对应的赋值运算符重载完成赋值。1.4 返回*this :要复合连续赋值的含义。

2023-07-30 19:08:46 96 1

原创 拷贝构造函数详解及存在的一些问题

d1传值给date′时,date′又要调动拷贝构造获得d1的值,此时date′调用拷贝构造,d1传值给date′′。d1传值给形参date时,date要调动拷贝构造获得d1的值,此时date调用拷贝构造,d1传值给date′。1. 拷贝构造函数的参数只有一个且必须是类类型对象的引用,使用传值方式编译器直接报错,在编译器生成的默认拷贝构造函数中,内置类型是按照字节方式直接拷贝的,而自定。字节序完成拷贝,这种拷贝叫做浅拷贝,或者值拷贝。时,则拷贝构造函数是一定要写的,否则就是浅拷贝。

2023-07-30 15:41:17 145 1

原创 NULL与nullptr的区别

程序本意是想通过Test(NULL)调用指针版本的Test(int*)函数,但是由于NULL被定义成0,因此与程序的初衷相悖。2. 在C++11中,sizeof(nullptr) 与 sizeof((void*)0)所占的字节数相同。在C++98中,字面常量0既可以是一个整形数字,也可以是无类型的指针(void*)常量,但是编译器。可以看到,NULL可能被定义为字面常量0,或者被定义为无类型指针(void*)的常量。3. 为了提高代码的健壮性,在后续表示指针空值时建议最好使用nullptr。

2023-07-28 22:56:45 56 1

原创 基于范围的for循环

此C++11中引入了基于范围的for循环。for循环后的括号由冒号“ :”分为两部分:第一部分是范。与普通循环类似,可以用continue来结束本次循环,也可以用break来跳出整个循环。对于一个有范围的集合而言,由程序员来说明循环的范围是多余的,有时候还会容易犯错误。对于数组而言,就是数组中第一个元素和最后一个元素的范围;begin和end的方法,begin和end就是for循环迭代的范围。围内用于迭代的变量,第二部分则表示被迭代的范围。注意:以下代码就有问题,因为for的范围不确定。

2023-07-28 18:09:23 104 1

原创 auto关键字的使用

在早期C/C++中auto的含义是:使用auto修饰的变量,是具有自动存储器的局部变量。C++11中,标准委员会赋予了auto全新的含义即:auto不再是一个存储类型指示符,而是作为一个新的类型指示符来指示编译器,auto声明的变量必须由编译器在编译时期推导而得。为了方便拼写类型,如std::map类型可用auto通过‘=’后面的表达式的类型推导出应该是什么类型。2. auto的使用return 10;

2023-07-28 17:56:58 85 1

原创 宏的优缺点?

1.没有类型的严格限制,如上宏函数可以传int,double等参数,增强代码的复用性。2.针对频繁调用小函数,不再建立栈帧,提高了效率。(因为预编译阶段进行了替换)2.导致代码可读性差,可维护性差,容易误用。1. 常量定义 换用const enum。2. 短小函数定义 换用内联函数。3.没有类型安全的检查。C++有哪些技术替代宏?

2023-07-28 16:37:26 88 1

原创 内联函数inline介绍及用法

以inline修饰的函数叫做内联函数,编译时C++编译器会在调用内联函数的地方展开,没有函数调。如果在上述函数前增加inline关键字将其改成内联函数,在编译期间编译器会用函数体替换函数的。2.inline对于编译器而言只是一个建议,不同编译器关于inline实现机制可能不同,一般建。1.inline是一种以空间换时间的做法,如果编译器将函数当成内联函数处理,在编译阶段,会。用函数体替换函数调用,缺陷:可能会使目标文件变大,优势:少了调用开销,提高程序运。用建立栈帧的开销,内联函数提升程序运行的效率。

2023-07-28 16:12:38 160 1

原创 命名空间,函数重载,引用等用法详解

1.命名空间的作用:在C/C++中,变量、函数和后面要学到的类都是大量存在的,这些变量、函数和类的名称将都存在于全局作用域中,可能会导致很多冲突。使用命名空间的目的是对标识符的名称进行本地化,以避免命名冲突或名字污染,namespace关键字的出现就是针对这种问题的。关于using namespace stdstd是C++标准库的命名空间名,C++将标准库的定义实现都放到这个命名空间中。自定义命名空间可解决这种问题2.命名空间中可以定义变量/函数/类型3.命名空间可以嵌套。

2023-07-22 17:03:14 35

原创 栈与队列的基本操作

栈与队列及循环队列的实现

2023-07-03 12:27:49 59 1

原创 二分查找介绍

二分查找介绍及注意事项

2023-03-15 21:27:50 35

原创 3.13学习笔记

new、delete以及new与malloc的区别

2023-03-13 22:32:47 41

原创 3.12学习笔记

&引用的好处、复杂空间复杂度的计算、malloc、calloc、realloc用法

2023-03-12 19:15:30 35

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除