当前位置: 首页 > 科技观察

C语言高效使用

时间:2023-03-13 17:31:31 科技观察

使用static关键字static关键字有两个作用。对于一个变量,表示该变量是一个静态变量,放在数据段中。即使函数结束,变量仍然存在。对于一个函数来说,意味着该函数的作用范围只在这个文件中,其他文件是访问不到的。这样做的好处是当文件只被本文件中的函数调用时,此时可以用static关键字修改。避免其他函数因函数名相同而报错,即使用this关键字修饰时,即使两个文件中的函数名完全相同,也不会报编译错误。比如下面有两个.c文件,分别是fun1.c和fun2.c。这两个文件中有个函数swap,函数名完全一样。所以我们可以像这样使用static关键字://fun1.cstaticvoidswap(int*a,int*b){inttemp;温度=*一个;*a=*b;*b=temp;}//乐趣2。cstaticvoidswap(int*a,int*b){inttemp;温度=*一个;*a=*b;*b=temp;}上面两个文件中有完全相同的函数,函数只能在各自的文件中使用。使用const关键字const关键字表示常量,即不变。在C语言中用作关键字,告诉编译器变量不能被修改。修饰变量修饰普通变量const用于修饰普通变量,表示变量的值不可修改,即只读。比如现在定义一个consta=10,那么以后a的值就不可修改了。常量一个=10;//初始化a=20//错误,a的值不可修改。修饰指针变量const用于修饰指针变量,表示指针的值不可修改。由于指针有两个可以修改的值,一个是指针的值,即指向的位置,另一个是指针指向的位置的值。为了区分这两个值是否可以修改,编译器规定采用“就近原则”,即const修饰最接近const。inta=1,b=2;constint*p=&a;//修饰的是int*,表示指针dequote不可修改,即指针指向的值不可修改,相当于intconst*p=&a;*p=10;//错误,p指针指向的值不能被修改p=&b;//正确,p指向的变量的值没有被改变。int*constq=&a;//修饰指针q,即指针q指向的位置不可修改位置修饰符数组const用于修饰数组,表示数组的所有值都不会被修改。通常,当编译器看到一个const数组时,它会将数组存储在代码区,即.text段,这样该数组将是只读数据。constinta[4]={1,2,3,4};a[1]=20;//错误,a数组的所有元素都不可修改。a数组是只读的,地址对齐变量放在代码段地址对齐地址对齐是一个很重要的概念。现代编译器提高了代码执行速度(主要与缓存结合)。默认情况下,地址对齐到4个字节,这是一个字对齐。现在让我们看一下下面的结构:structtest{chara;intb;}如果不了解地址对齐概念的读者可能会认为上面的结构一共占用了1+4=5个字节,实际上占用了8个字节byte,编译器会将其对齐4个字节。由于a变量只占一个字节,后面的b变量占4个字节。如果只给一个字节地址,编译器会检测到b变量的地址和它没有对齐4字节,所以编译器默认会将分配给b变量的地址偏移3字节,这样的地址b变量正好是四字节对齐的。#include结构测试{chara;intb;};intmain(intargc,char**argv){structtesta;printf("structtest的大小为=%d\n",sizeof(a));return0;}structuresshshishi'jshi'ji是实际的结构。因此,在定义结构时为了尽可能节省空间,必须考虑字节对齐。让我们比较一下这两个结构:#includestructA{inta;字符b;短c;};结构B{字符b;诠释;shortc;};intmain(intargc,char**argv){structAst1;结构Bst2;printf("st1的大小为=%d\n",sizeof(st1));printf("st2的大小为=%d\n",sizeof(st2));return0;}运行后结果如下:两个相同的结构体,只是变量存放位置的不同导致最终占用的空间不同,这是字节对齐的结果。显然结构A需要节省内存。指针地址对齐既然指针是变量,那么指针是否可以进行位操作呢?比如清除指针值的最后一位:p&=(~(1)),理论上应该是可行的,因为指针是一个变量,但实际上编译器并不高兴,它认为这样会导致totheaddresspointedbythepointer太随意了,没有严格遵循类型空间的大小,导致指针无法进行位操作。理论上位运算和算术运算是等价的,所以也可以自己实现指针位运算。这个重载在C++运算符中可能更方便,这里就不详细讲指针的位操作了。