C语言进阶之C语言关键字

基本数据类型

1.数据类型

  • 数据类型可以理解为固定内存大小的别名(例如,在C语言中int数据类型代表了4个字节的内存)
  • 数据类型是可以创建变量的模板

数据类型的本质就是固定字节别名

2.变量

  • 变量是一段实际连续存储空间的别名
  • 程序中通过变量来申请并命名存储空间
  • 通过变量的名字可以使用存储空间

auto,register,static分析(属性关键字)

  • C语言中的变量可以有自己的属性
  • 在定义变量得时候可以加上“属性”关键字
  • “属性”关键字指明变量具有特有意义(例如static修饰的关键字,具有特殊的意义是使修饰的变量的生命周期与程序的生命周期同步)

auto(在程序的栈上面)

  • auto即C语言中局部变量得默认值。
  • 编译器默认所有的局部变量都是auto的

最佳示例

写一个简单的打印数字的程序

#include<stdio.h>
int main(){auto  int a =10;printf("%d",a);
}

你会发现auto 似乎并没有什么软用

static(在内存的静态区里面的变量)

  • static修饰的全局变量作用域只是申明的文件中

最佳实例一

新建两个.c文件,分别为test.ctest2.c

test.c

#include<stdio.h>
extern int test2_g;
int main()
{printf("%d",test2_g);return 0;
}

test2.c

static int test2_g=1;

我们尝试用用gcc编译两个.c文件,会报一个未定义应用的错误。如果,我们把test2.c中的static去掉,程序就和我们预想的结果相同。也就是说static让变量test2_g私有化了。在C语言面向对象编程中,可以完全将它作为private来用。

如果我们需要访问这个变量,也是有办法的。正如其他面向对象语言中一样,我们可以写一个get方法来获取它的值。我们修改test2.c这个文件。

static int test2_g=1;
int get_test2_g()
{return test2_g;
}

再修改test.c这个文件

#include<stdio.h>
extern int  get_test2_g();
int main()
{printf("%d", get_test2_g());return 0;
}

两句话总结static

  1. static存在内存的静态存储区,有着和程序一样长的生命周期。
  2. static修饰的函数作用域只是申明的文件中(也就是说只能在一个C文件中)。相当于java中的private

##register(用在非常讲究性能的实时系统中,通常嵌入式工程师才需要)

  • register关键字指明将变量存储于寄存器中
  • register只是请求寄存器变量,但不一定成功

注意:

register变量得必须是CPU寄存器可以接受的值
不能用&运算符获取register变量的地址

总结

  1. auto变量存储在程序的栈中,默认属性只能是局部变量
  2. static变量存储在程序的静态区
  3. register变量存储请求存储于CPU寄存器中只能是局部变量
  • 全局变量与静态变量在程序的全局&&静态数据区

if,switch,do,while,for分析

分支语句

bool数据类型

C语言中默认是没有bool类型(标准为C99),实际项目开发又十分需要bool类型我们可以自己创建一种新的数据类型。

typdef enum _bool{FALSE,TRUE
}BOOL;

使用

bool a;
if(a)
{}

if注意点

  • bool型变量应该直接出现于条件中,不要进行比较。

    • 例如if(True==True)这样的写法。
  • 普通变量和0(或其他常数)比较时,0值应该出现在比较符号的左边(经验!!!)

    • 举例子

      在项目开发中我们需要一个变量与常数比较,例如

      #include<stdio.h>
      int main(){int a=90;if (a==100){//todo}
      }

      如果我们手贱写将a==100写成a=100

      #include<stdio.h>
      int main(){int a=90;if (a=100){//todo}
      }
      

      很显然的是编译仍然通过,但是程序逻辑是不对的.

      如果我们在对常数的比较中,采用

      #include<stdio.h>
      int main(){int a=90;if (100==a){//todo}
      }
      

      这样的写法,手抖少写个等号又何妨。

  • float型变量不能直接进行0值比较,需要定义精度

  • 因为对于不同的系统,float的精度不一样,所以,是有必要进行这种比较的

    #define ESPINON 0.0000 0001
    float f=0.0f;//如果不定义精度,很有可能出错if((-ESPINON<=f) && (f<=ESPINON))
    {}
    

switch注意事项

  • case语句中的值只能是整型或字符型
  • case排列顺序的分析
    • 按字母或者数字顺序排列各条语句
    • 正常情况放前面,异常情况放在后面
    • default语句只能用于处理真正的默认情况
    • 单值
  • 每个case语句分支必须有break,否则分支重叠。

#分支语句的总结

  • if按片,switch对每个离散值来判断
  • if可以替代switch,但是switch不能取代if
  • switch在多分支里,比较简单

循环语句

  • 循环语句的基本工作方式

    • 通过条件表达式判定是否执行循环体
    • 条件表达式遵循if语句表达式的原则
  • do,while,for的区别
    • do先执行后判断,也就是说必须执行一次
    • while语句先判断后执行,循环体可能不执行
    • for语句先判断后执行,相比while更简洁
   if(n>0){do{ret +=n--;}while(n);              }
  • break和continue的区别

    • break表示终止循环的执行
    • continue终止本次循环

switch能否用continue?
不能

##do和break的妙用(一般程序设计分析)

do{//todo
}while(0)//作为一种代码块的作用
free(p);

#goto,void,extern,sizeof分析
##goto

  • 你一定是有特殊技巧,才用的吧
    ##void的意义
  • 如果函数没有返回值,那么应该将其声明为void型
  • 如果没有参数,应该声明其参数为void

表示无

void指针的意义

  • C语言规定只有相同类型的指针才可以相互赋值

  • void*指针作为左值用于“接收”任意类型的指针

  • void*指针作为右值赋值给其他指针时需要强制类型转换

    • 大名鼎鼎的malloc就是void *类型的

extern中隐藏的意义

  • extern 用于声明外部定义的变量和函数

  • extern 用于“告诉”编译器用C的方式编译,这里有一篇更加深入的文章extern "c"用法解析

    extern “C”
    {
    //todo
    }

    
    > 为什么要这样做呢?因为有些编译器在编译的时候,自以为是的优化,导致程序无法正常运行。
    >
    > 还有就是在CPP中用C代码

sizeof

  • sizeof是编译器的内置指示值,不是函数

    • 为什么呢?我是如何知道的呢?通过三点

      1. 一般系统函数在C语言预处理的时候,都会通过extern引入到预处理文件,然而sizeof并没有。

      2. 你见过C语言有可以接受数据类型的数据类型么?

      3. //上下一样的,所以sizeof这个叼毛不是函数
        sizeof(a);
        sizeof a;
        
  • sizeof用于“计算”相应的实体所占的内存大小

  • sizeof的值在编译期就已经确定

const和valatile分析

const(是可以修改的)

  • 在C语言中const修饰的变量时只读的,其本质还是变量
  • const修饰的变量会在内存占用空间
  • 本质上const只对编译器有用,在运行时无用
  • 在C语言中const修饰的数组是只读的
  • const修饰的数组空间不可被改变(编译器的过,通过指针不能改变,gcc就不行)

const修饰指针

const int* p; //p可变,p指向的内容不可变
int const* p;//p可变,p指向的内容不可变
int* const p;//p不可变,p指向的内容可变
const int* const p;//p和p指向的内容都不可变

最佳实例

**口诀:左数右指 **
指针符号在const左边的时候指针所指向的数字不能发生改变,右边的时候

左数
void main()
{int i=0;int const * p=&i;* p=3;
}
右指
#include<stdio.h>
void main()
{int i=0;int * const p=&i;* p=3;p=NULL;
}

const修饰函数参数和返回值

  • const修饰函数参数表示在函数体内不希望改变参数的值
  • const修饰的函数返回值表示返回值不可改变,多用于返回指针
    最佳实例
#include<stdio.h>
const int * func()
{int i=0;i++;return & i;
}
int main()
{const int * q=func();printf("%d\n",*q);
}

valatile

  • volatile可理解为“编译器警告指示字”
  • volatile用于告诉编译器必须每次去内存中取变量值
  • volatile主要修饰可能被多个线程访问的变量(有没有java 的味道)
  • volatile也可以修饰可能被未知因数更改的变量

struct和union分析

由结构体产生柔性数组

  • 柔性数组既数组大小待定的数组
  • C语言中结构体的最后一个元素可以是大小未知的数组
  • C语言中可以由结构体产生柔性数组

柔性数组实例

struct SoftArray{int len;int array[];
};

柔性数组Dome

#include<stdio.h>
#include<malloc.h>
typedef struct _SoftArray{int len;int array[];
}SoftArray;
int main()
{int len=10,i=0;SoftArray *p=(SoftArray*)malloc(sizeof(SoftArray)+sizeof(int)*len);p->len=len;for(i=0;i<len;i++){p->array[i]=i+1;}for(i=0;i<len;i++){printf("%d\n",p->array[i]);}return 0;
}

使用柔性数组创建斐波那契数列

#include<stdio.h>
#include<malloc.h>
typedef struct _softArray{int len;int array[];
}SoftArray;
SoftArray * creat_Array(int size)
{SoftArray *p=NULL;if(size>0){p=(SoftArray*)malloc(sizeof(SoftArray)+sizeof(int)*size);p->len=size;}return p;
}
void del_Array(SoftArray * p)
{free(p);
}
void create_Fibonacci(SoftArray* p)
{int i=0;if(NULL!=p){if(1==p->len){p->array[0]=1;}else{p->array[0]=1;p->array[1]=1;if(p->len>2){for(i=2;i<p->len;i++){p->array[i]=p->array[i-1]+p->array[i-2];}}}}
}
int main()
{int i=0;SoftArray * my=creat_Array(10);create_Fibonacci(my);for(i=0;i<10;i++){printf("%d\n",my->array[i]);}del_Array(my);return 0;
}

记得释放数组(和JavaSE不同)

union和struct的区别

  • struct 中的每个域在内存中都独立分配空间
  • union只分配最大域的内存空间

区别的最佳实例

#include<stdio.h>
#include<malloc.h>
struct A{int a;int b;
};
union B{int a;int b;
};
int main()
{printf("struct is %d\n",sizeof(struct A));//结果为8printf("union is %d\n",sizeof(union B));//结果为4return 0;
}
  • union受系统大小端的影响

    • 学过操作系统的人都知道系统有大小端之分,一般来讲我们的PC,迫于某大厂,所以是小端的

      测试电脑是大端还是小端的程序

      #include<stdio.h>
      int checkSys()
      {union check{int i;char c;}cc;cc.i=1;return cc.c;
      }
      int main()
      {if(1==checkSys())printf("小端\n");elseprintf("大端\n");return 0;
      }
      

      上面程序的原理是:

      因为union分配最大数据类型的空间,如果是大端模式的话,高地址先被分配到,被赋值为1,我们调用cc.c 取的是低地址,应当是0.。小端的话反之则反。

枚举类型

  • enum是一种自定义类型
  • enum默认常量在前一个的基础上依次加一
  • enum类型的变量只能取定义时的离散值
enum Color{GREEN,RED=2,BLUE
};

enum 默认的第一个是0,也就是说上面代码段中GREEN为0,BLUE为3

枚举类型与#define的区别

#include <stdio.h>
#define YELLOW 1
int main() {enum Color{GREEN,RED};if (YELLOW ==GREEN){}return 0;
}

我们用gcc -E 处理一下这个程序,然后会发现原本的程序变成

....
int main() {enum Color{GREEN,RED};if (1 ==GREEN){}return 0;
}

区别全在程序里,程序本身没有意义

typedef

  • typedef用于给一个已经存在的数据类型重命名
  • typedef并没有产生新的类型
  • typedef从定义的类型不能进行unsigned和signed扩展

3131字带你进阶C语言中的关键字相关推荐

  1. 编程c语言中_是什么意思,计算机C语言中的关键字:double是什么意思?

    用户提问 RT 推荐答案 double:表示双精度字型. C语言中的关键字: auto :声明自动变量 break:跳出当前循环 case:开关语句分支 char :声明字符型变量或函数返回值类型 c ...

  2. 在c语言中保留字是有专门含义和作用的,c语言中的关键字和保留字的区别?

    c语言中的关键字和保留字的区别?以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容,让我们赶快一起来看一下吧! c语言中的关键字和保留字的区别? 在C语 ...

  3. C语言中的关键字详略

    首先我们要注意:在C语言中define不是关键字.define是编译器的预编译指令,是编译器实现的,不是C语言的内容. C语言编译器不认识#开头的东西,那些是预处理的事情. C编译器看到的是预处理完成 ...

  4. C语言中的关键字概览

    文章目录 1 C语言中的关键字概览 1 C语言中的关键字概览 C语言中一共有32个关键字,如下: 参考资料: C语言深度解剖

  5. C语言中的关键字,变量的定义,变量的命名规则,交换两个变量的值,驼峰命名法【 C语言变量名命名法则】

    C语言结构 C语言中的关键字 变量 变量的定义 变量的命名规则 交换两个变量的值 驼峰命名法 C语言结构 上图中我们可以看到最外层是程序,内部是所有的构成,我们从最里面开始说明. 当我们用计算机语言来 ...

  6. c语言中关键字的含义,c语言中的关键字有哪些?有什么含义?

    c语言中的关键字有哪些?有什么含义? 发布时间:2020-04-23 09:33:30 来源:亿速云 阅读:174 作者:小新 这篇文章主要介绍了c语言中的关键字有哪些?有什么含义?,具有一定借鉴价值 ...

  7. C语言中的关键字“ volatile”的用法(摘)

    C语言中的关键字" volatile"的用法(摘) volatile 这个ANSI C 关键字在经典的C 教程中很少提及,高层编程的人也可能永远都 不会用到,但是作为嵌入式开发者来 ...

  8. c不能做oracle关键字,C语言中的关键字不能作变量名,但可以作为函数名。

    语言中目的工助学中心的立勤成是(. 个运在整程中输过,键字它们是(,个单重要的据是有三非常. 作变作包括运输费率.自动下级部门继承,目选择不能不同的科,目部门的折旧科设置上级.故用固定管理资产系统不 ...

  9. 同一主机的多个子进程使用同一个套接字_如何在Go语言中使用Websockets:最佳工具与行动指南...

    如今,在不刷新页面的情况下发送消息并获得即时响应在我们看来是理所当然的事情.但是曾几何时,启用实时功能对开发人员来说是一个真正的挑战.开发社区在HTTP长轮询(http long polling)和A ...

最新文章

  1. 知识星球作业(第5周) - 关于view的知识
  2. GO语言Windows下Liteide
  3. asp.net用Zxing库实现条形码输出
  4. oracle终止dbms调度,Oracle使用DBMS_JOB创建的数据库作业,遇到数据库关闭状态的调度...
  5. easyui中的datetimebox 只显示年月日_设置Win10任务栏显示星期几方法
  6. 当你在应用机器学习时你应该想什么
  7. 谈谈怎样提高炼丹手速
  8. StringEscapeUtils类的使用
  9. 微信小程序开发-微信登陆流程
  10. java 的SYSTEM类
  11. vscode 单击跳转 ctrl+鼠标左键不能跳转到函数或变量的定义
  12. 串珠问题(今日头条笔试)
  13. c语言叠阵题目怎么做,选出下列词语书写全正确的一组[]A、贪婪点辍忍军不禁玲珑剔透B、辜负骚扰擎天旱地多姿多采C、小憩茁壮怡然自得头昏目眩D、玷污糟蹋蜂围叠阵明察秋豪...
  14. C程序内存泄露检测工具——Valgrind
  15. 水花兄弟(Splash Brothers)
  16. vwf活性_血管性血友病因子(VWF)应该针对血型设置参考范围吗?
  17. 用python造数据
  18. iPhone删除面部解锁忘记了密码
  19. 在线翻译html网页,HTML网页到维基页面翻译器
  20. Java获取当前时间前24小时时间

热门文章

  1. 10英文图片网站 值得你收藏
  2. Joint Extraction of Retinal Vessels and Centerlines Based on Deep Semantics and Multi-Scaled Cross-T
  3. 小程序毕设作品之微信美食菜谱小程序毕业设计成品(5)任务书
  4. 黄色固体或黄色油状物PC Biotin-Azide;photoclevable Biotin-N3是可分解的生物素
  5. 用移动硬盘安装win7(制作启动盘)
  6. 造梦西游online十殿阎罗篇(下)(莫等闲,空悲切)
  7. 影视APP源码电视盒子源码对接苹果CMS后台新增蓝光
  8. 中小型企业网络局域网实例-拓扑与规划
  9. SQLservet使用DATEADD获取一小时前的时间
  10. Vue项目引入Echarts可视化图表库教程踩坑