- 博客(23)
- 收藏
- 关注
原创 Linux高级编程-进程间通信(IPC)
它通过一对文件描述符提供了一个半双工的通信通道,即一个进程可以写入数据到管道的写端,另一个进程从管道的读端读取数据。创建无名管道的进程(通常是父进程)在 fork 调用之后,子进程会继承父进程的文件描述符,允许父子进程通过管道进行通信。与普通文件不同,管道不支持 lseek 和 fseek,因为它们的读取是基于流的,不像普通文件那样可以随机访问。:如果管道的读端被关闭,而写端仍存在,写操作会失败,通常返回 EPIPE 错误(Broken pipe)。如果管道为空,读操作会阻塞,直到管道中有数据可读。
2024-09-01 23:08:27
910
原创 Linux高级编程7 - 线程控制
要引入线程控制这个概念是由于在多线程中存在资源竞争的问题,导致结果与想的不一样。比如这个程序,想实现的A加到10000去。#include <stdio.h>#include <stdlib.h>#include <unistd.h>#include <pthread.h>int A = 0 ;void * th(void* arg){ int i = 5000; while(i--) {
2024-08-29 22:39:54
650
原创 Linux高级编程6 - 线程
它用于释放线程在运行过程中申请的资源,确保程序不会出现资源泄漏,在大型项目中子线程申请的资源可能会在别的函数里使用,所以不可能该子线程结束了就清除资源,应该在其它地方使用后,统一清除这些资源才用这2个函数清除资源pthread_cleanup_push 和 pthread_cleanup_pop。线程:线程是程序执行的基本单位,一个程序可以包含多个线程,每个线程执行不同的任务,但共享同一进程的地址空间。都是用于管理线程生命周期的函数,它们的主要功能是处理线程的退出和资源回收,但它们的用途和使用方式不同。
2024-08-21 22:57:08
736
原创 Linux高级编程5 - 进程的退出与调用函数
调用 exit函数时 退出状态,终止的进程会通知父进程,自己使如何终止的。exit()、_exit()等这些函数执行,只会将结束自生的进程内存空间(3G)、但是该进程的PCB块还是存在内存中的,要至少父类程序调用wait(),waitpid()才能清除子类的PCB块。status:退出时返回的状态码,通常为0表示成功,非0表示错误,status存放8字节的整数、最大255,大于255的数会被截断。1. 清理已打开的流: 所有用 fopen打开的文件流都会被关闭,缓冲区中的数据也会被刷新到相应的文件中。
2024-08-20 22:37:24
1256
原创 Linux高级编程3 - 目录、用户与组、出错相关函数、时间函数
1、opendir 用于打开一个目录,并返回一个目录流指针。name:要打开的目录的路径。返回值:成功时返回指向目录流的指针,失败时返回 NULL。readdir用于读取目录中的一个条目(如文件或子目录)。每次调用会返回下一个目录条目,直到所有条目都读取完毕.dirp:通过opendir打开的目录流指针。返回值:成功时返回指向目录条目的指针,失败时返回 NULL。struct dirent结构通常包含以下成员:d_name:文件或目录的名称。d_ino:文件的索引节点号(inode number)
2024-08-15 22:48:55
1184
原创 Linux高级编程2 - 标准I\O与文件I\O
文件I/O系统调用: 文件I/O系统调用是操作系统提供的一组函数,允许用户程序与文件系统进行交互,包括创建文件、打开文件、读取文件内容、写入文件内容、关闭文件等操作。功能:ftell用于获取当前文件指针在文件中的位置,通常用于之后的fseek操作,以便能够恢复到当前的文件位置。注意:如果从文件的指定位置向后偏移过程中已经超过了文件的当前末尾位置,则会自动以'\0'来填充文件内容,从而形成一种被称为"空洞文件" 的特殊文件。功能: 关闭一个已打开的文件描述符,释放与该文件相关的资源。
2024-08-13 21:43:11
2174
原创 Linux高级编程1-标准I\O
成功时返回实际读取的块数(通常等于 nmemb,除非遇到文件末尾或读取错误).如果遇到文件末尾或发生错误,返回的块数可能小于 nmemb.stream:指向文件的指针,表示要读取的文件。成功时返回读取的字符(以 int类型返回),如果到达文件末尾(EOF),或者发生读取错误,则返回 `EOF。filename 是要打开的文件的名称,mode 是打开文件的模式,例如读取、写入或追加。如果你使用 fputs() 来写入二进制数据,任何遇到的空字符都会被认为是字符串的结尾,导致数据写入不完整。
2024-08-12 21:47:36
771
原创 枚举、typedef、位运算
typedef是 C 语言中的一个关键字,用于为现有的数据类型定义新的名称或别名。按位或运算符对两个操作数的每一位执行“或”操作:如果两个相应的位中至少有一个是1,则结果位为1,否则为0。按位异或运算符对两个操作数的每一位执行“异或”操作:如果两个相应的位不同,则结果位为1,相同则为0。按位与运算符对两个操作数的每一位执行“与”操作:如果两个相应的位都是1,则结果位为1,否则为0。它用于定义一组相关的常量。:通过 typedef,你可以为不同平台上的数据类型定义统一的别名,从而在不同平台上使用相同的代码。
2024-08-11 13:36:25
748
原创 结构体与共用体
内存对齐要求数据在内存中的起始地址必须是某种特定的地址倍数。例如,假设一个系统要求4字节的整数类型(int)必须存储在4的倍数地址上(如0x0000、0x0004、0x0008等),否则会导致访问效率下降甚至产生错误,一个数据被拆分为多次次读取、读取后还要进行合并,才能得到一个数据、导致效率低,所以要内存对齐。2.为什么要内存对齐提高内存访问效率:许多处理器在访问内存时,如果数据存储在一个对齐的地址上,会比访问非对齐的数据更快。
2024-08-10 00:07:01
2764
原创 C语言2 - 数组指针、指针数组、指针函数
如何区分数组指针与指针数组,数组指针是指针。指针数组是数组。可以通过对他们的优先级进行比较。可以根据语句中的优先级来判断,用下面的例子来说明区分这两种char * a[3]:这个优先级最高的a[3]所以是一个数组变量,然后就是数组的类型了,char *说明该类型是char类型指针,所以为指针数组。char (*a)[3]:这个中()的优先级高下,所以是一个指针变量,然后再看类型为一个数组类型的,所以叫数组指针。:数组指针是一个指向数组的指针。
2024-08-08 20:11:35
895
1
原创 const与指针2
在C语言中,const关键字用于定义常量或不可修改的变量。它可以用于基本数据类型、指针以及函数参数。以下是const当const用于基本数据类型时,变量的值在初始化后不能被修改。修饰全局变量时:不能通过值和地址去修改它,更不能要变量给它赋值。修饰局部变量时,第一次赋值是可以的,也可以通过变量给它赋值。之后不能通过直接赋值,但是通过地址去修改它(有警告、可以运行)。const在指针中的使用稍微复杂一些,根据const的位置不同,含义也不同.
2024-08-07 22:01:30
611
原创 C语言指针1
为什么要使用指针这个呢,之前学过函数,函数是传值的,主函数执行这个函数后并不会交换a、b的值,因为函数参数传的值,并没有把它的地址传过去。指针也是一种数据类型(指针类型),指针变量就是用来存放地址的变量、在同一系统下、不同类型的指针变量占用的存储单元长度是相同的。2、偏移量sizeof(基类型)的大小空间,这个基类型是指针声明是的这个声明是(int ),而不是变量的基类型。*p为char类型指针,char只有1个字节,所以它偏移量就为1,也可以理解为*p为一个char类型的变量,占1个字节的空间。
2024-08-06 19:50:31
286
原创 C语言预处理
在声明宏函数时,尽量把每个变量都加上一个括号以及最外面加上一个括号,免得出现意料之外的结果,宏函数的本质还是替换,不会考虑运算符优先级的问题。2、使用不一样:宏定义:在预处理阶段就结束了,宏定义的使用只是进行文本原样替换,不进行语法检查。函数:调用时进行使用、函数的使用本质上是函数代码的调用,函数参数是有类型的,编译阶段是要进行类型检查的。将代码中相关的预处理命令执行、最终生产一个只包含C语言代码的文件,预处理不是C语言的一部分,是编译器的一部分。C语言编译过程分为:预处理、编译、汇编、链接。
2024-08-05 21:03:53
690
原创 函数(形参为数组)、变量和函数的作用域、生命周期
3.存放内容不同:栈存放返回函数地址,寄存器等,堆顶有一个字节大小的堆,程序员手动填充。通过extern,可以在多个文件中访问同一个全局变量或函数,但static修饰的变量或函数不能被外部文件访问。关键字用于建议编译器将某个变量存储在CPU的寄存器中、寄存器变量可以比存储在内存中的变量更快地被访问,因为寄存器是CPU内部的高速存储器,不需要重复将数据从内存拿到CPU中。一维整型数组做做形参列表,需要数组名+长度,传数组名其实就是将数组的首地址(传指针)传给形参,而在64位的系统下,指针占8字节;
2024-08-04 11:31:11
1399
原创 函数与递归
函数执行流程是先从入口函数main()进入,执行到maxOfArryay()函数,程序会在main()函数里的数据存到栈(先入后出)里去,程序计数器跳到maxOfArray()地址去执行,执行到fun1(),程序将fun1执行过的数据存到栈里去,然后跳到fun1执行,遇到printf()又将执行过的数据存到栈中去,跳到printf()中执行去,执行完后,将fun1()栈顶的数据拿回,继续执行fun1,直到执行完后,fun1中的局部变量的空间释放。问题: 古印度有一个梵塔,塔上有3个座,A,B,C。
2024-08-02 22:07:51
870
原创 二维字符串及函数
首先要确定函数名,取名尽量与要实现的功能一致容易,能一眼看懂这个函数要实现的功能;:在编程中为了重复使用而预先编写好的函数集合,这些函数通常被组织在库(library)中。当你需要使用这些函数的功能时,可以通过包含相应的头文件(使用 `#include` 指令)并将库链接到你的程序中来调用它们。在C语言中,标准库函数包括了如 `printf`、`scanf`、`strlen` 等常用的函数,这些函数定义在标准头文件中。个数匹配:传递给函数的实际参数的数量必须与函数声明中的形式参数数量一致。
2024-08-01 21:53:25
492
原创 C语言1 - 字符串函数
strncmp(const char* str1, const char* str2,size_t n),这里 `str1` 和 `str2` 分别是指向待比较的两个字符串的指针,`n` 是要比较的字符数,比较字符串str1和str2前n个字符是否相同,区分大小写。这里 `dest` 是目标字符串的指针,`src` 是源字符串的指针,`num` 是要从 `src` 中复制的最大字符数(不包括空终止符)。这里 `dest` 和 `src` 分别是指向待比较的两个字符串的指针、区分大小写。
2024-07-31 21:19:12
712
原创 C语言3 - 排序与查找
s1的存储地址会在s的周围进行存储的,这里是在s前面存储,存储位置要看系统决定的。输入s1时 输入“1234567”长度超过给定的长度,导致将字符串“67”写入到s所在的地址中导致“hel”数据被gets()修改了,所以输出才为67,输入字符串时会默认补’\0‘通过多次遍历待排序的数组,每次比较相邻的两个元素,如果它们的顺序错误就交换它们的位置。时间复杂度:主要衡量的是一个算法的运行速度,而空间复杂度是衡量一个算法所需要的额外空间。gets(),输入字符串,已被弃用,容易修改到其它数据的内容。
2024-07-30 21:56:18
2209
原创 逻辑运算符和控制语句
swtich选择语句时要在case执行完后加上break,不然的话下面的case语句不会再进行判断了,直接执行case里的语句。表达式1||表达式2.,如果表达式1或表达式2有一个为真,该表达式为真。要注意表达式1为真的话,表达式2不会被执行。表达式1&&表达式2,如果表达式1或表达式2有一个为假,该表达式为假。要注意表达式1为假的话,表达式2不会被执行。其中非零的数则为真(负数也是真),0(NULL、'\0',0)则为假。选择语句根据条件判断执行分支的路线。循环语句是要反复执行的语句。
2024-07-29 20:51:50
284
原创 输入输出函数
是为了保证移植性和通用性好,而实际应用中,ANSI C库包含大量的UNIX I/O函数,所有系统都通用的标准I/O函数、ANSI C标准发布后,C把stdio.h头文件与getchar()和putchar()相关联。使用printf()函数打印数据指令要与打印数据类型相匹配,例如打印整数时使用%d,打印字符时使用%c。scanf()转换说明与printf()函数得转换说明几乎相同,主要区别在浮点型,printf()都使用%f、%e、%E、%G、%g转换说明,而在scanf中是下表得转换说明。
2024-07-26 20:22:21
719
原创 C数据类型及运算符
长类型----->短类型会导致高位截断(ua)。,要区分先用还是先加(减),a++(--)是先用值后在赋值、而(--)++a则是先加再赋值。常见的运算符:"+"、"-","*","/","%","++","--"。赋值运算常见的赋值运算符有"="、"+="、" -="、" *="、" /="。: 赋值运算符左侧的变量减去右侧的值 , 然后将运算结果赋给左侧的变量。:赋值运算符右侧的值对左侧的变量取余 , 然后将运算结果赋给左侧的变量。:赋值运算符左侧的变量乘以右侧的值 , 然后将运算结果赋给左侧的变量。
2024-07-25 20:38:01
850
原创 Linux C基本类型介绍
%hd”,表示打印有符号int的一半(2位),而short就是2位的。输出端a=-1是因为“%hd”打印有符号型的会把65535(1111 1111)最高位做为符号位1,即表负数的补码,通过反码+1负数原码即(-1);整型中分为short(短整型)、int(整型)、long(长整型)、long long(长长整型)。如图2."%hu"表示无符号的2位整型。当变量a1运算大于signed short的取值范围时,则会保留低16位数据、高位的会被丢弃即为(0x00 00 00 01),所以hu:a1=1。
2024-07-24 21:00:56
349
原创 Linux常用指令及vim编辑器
打开多个文件:vsp (:sq)文件名;Linux@Ubuntu:~(/)$,“Linux”当前用户、“@”分隔符、“Ubuntu”主机名、“:”分隔符、“$”普通用户、“~”:表示用户目录、“/”:根目录。ls -l(lh) 查看文件属性 、"l":文件大小用byte、“lh”:文件大小用K、M、G等。Linux下文件访问系统是:系统启动、虚拟根文件系统、挂载硬盘、访问硬盘上的文件(Linux下一切都为文件)Linux下编译可分为四部:vi/vim编辑、gcc(编译)、.out(运行)、gdb(调试)。
2024-07-23 21:00:41
251
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人
RSS订阅