第一章 “C“浒传——初识C语言(更适合初学者体质哦!)
目录
系列文章目录
前言
一、什么是C语言
二、第一个C语言程序
三、数据类型
四、变量,常量
4.1 定义变量的方法
4.1.1 变量的命名
4.2 变量的分类
4.3 变量的使用
4.4 变量的作用域和生命周期
4.4.1 作用域
4.4.2 生命周期
4.5 常量
4.5.1 字面常量
4.5.2 const 修饰的常变量
4.5.3 #define 定义的标识符常量
4.5.4 枚举常量
五、字符串+转移字符+注释
5.1 字符串
5.2 转义字符
5.3 注释
六、选择语句
七、循环语句
八、函数
九、数组
9.1 数组定义
9.2 数组的下标
9.3 数组的使用
十、操作符
10.1 算术操作符
10.2 移位操作符
10.3 位操作符
10.4 赋值操作符
10.5 单目操作符
10.6 关系操作符
10.7 逻辑操作符
10.8 条件操作符
10.9 逗号表达式
10. 10 下标引用、函数调用和结构成员
十一、常见关键字
11.1 关键字 register
11.2 关键字 typedef
11.3 关键字 static
11.3.1 修饰局部变量
11.3.2 修饰全局变量
11.3.3 修饰函数
十二、#define 定义常量和宏
12.1 #define定义标识符常量
12.2 #define定义宏
十三、指针
13.1 内存
13.2 指针变量的大小
十四、结构体
想必,有些童鞋刚接触到C语言,就像小编我一样根本不知道C语言究竟在讲的是什么?那么恭喜你,你发现了一个宝藏。那么,废话不多说,就请跟随小编的脚步进行了解初识C语言吧!
正如题目所说,初始C语言是对C语言有一个大概的认识,搭建起C语言的框架。那么,小编要开始讲解了。 记得这一章主要是初始C语言的一个大纲,内容中含有大量的链接是为了详细地讲解每一部分的内容。
首先,请你先用自己的话解释C语言是什么?(这个要画重点,有可能面试官会问)
**********************************************************************************************
语言:汉语,日语,英语等。语言是一个自然语言,是人与人交流的语言。
计算机语言:类比过来,是人与计算机之间的交流。
***********************************************************************************************
C语言是一门通用计算机编程语言(这就是C语言牛逼的地方),广泛用于底层开发。
如果读者想要了解更多有关C语言的功能与作用,在度娘中,你可以点击这个链接: C语言的作用与功能 。
对于底层开发,下面进行解释一下:一般地,电脑分为上层软件和下层软件,而下层软件是底层,C语言就广泛应用于底层开发。
计算机处理的是“二进制的信息”(这个点很重要,因为以后如果讲与内存有关的内容要带入这个点)。在进行C语言的学习中,我们需要使用集成开发环境。集成开发环境是集成了很多的子程序:编辑、编译、链接、运行、调试。(小编我也正在了解这些内容,就不好帮你们讲解这部分内容,如果感兴趣的话,小编就在这里为大家介绍一本书:《程序员的自我修养——链接、装载与库》。这本书详细解说了这五个步骤是起到什么作用。等小编读完后,定会做一篇博客进行讲解与分析。)
*******************************************************************************************************
我们在了解完C语言是什么后,我们需要了解如何使用集成开发环境去完成第一个C语言程序。下面,大部分人在初学C语言时,都不会使用的集成开发环境。小编我也会带着大家如何使用VS2019,因为其他编译器都太古老了。看下面的图进行你的第一步吧!
********************************************************************************************************
*******************************************************************************************************
在进行计算机语言的学习中,有一个梗就是"hello world",因为基本大家的第一个C语言程序都是从"hello world"开始的,那么对于一个这么简单的程序,我们可以从中学习到什么呢?
*******************************************************************************************************
#include
int main()
{
printf("hello world\n");
return 0;
}
首先,可以知道C语言中所有字符都是英文的字符。其次,在c语言代码中都是从main函数的第一行开始的,main函数是程序的入口,一个工程中main函数有且只有一个。其中代码中的printf函数是编译器自带的函数,可以直接使用。最后,
最后再讲一下main函数:main函数有三种写法,第一种就是 int main()(这个是最简单的,也是我们最常用的);第二种是 int main(void),这种写法中明确表示main函数不接收参数;第三种是 int main (int argc , char* arr[]),在这样写的时候,有两个参数被送给了main(),一个参数是描述了命令行参数的个数,一个是命令行中的数组,通常称为argv,命令行参数都是字符串。详情请看这条链接:【命令行参数_百度百科】
*******************************************************************************************************
C语言的数据类型有:char(字符数据类型) short(短整型)
int(整型) long(长整型)
long long(更长的整型) float(单精度浮点数) double(双精度浮点数)。
*******************************************************************************************************
在了解数据类型前,我们先探究为什么要写程序?是为了用程序解决生活中的一些问题。在现实生活中,我们的各种数据有很多不同的类型,为了更加丰富的表达生活中的各种值,所以在C语言程序中设置这么多数据类型。
每种类型的大小是多少?
******************************************************************************************************* 在这里提一句计算机中常见的单位:bit(比特),byte(字节),KB,MB,GB,TB,PB。他们的单位换算为:1 byte = 8 bit
1 KB = 1024 byte
1 MB = 1024 KB
1 GB = 1024 MB
1 TB = 1024 GB
1 PB = 1024 TB。
*******************************************************************************************************
在生活中有些值是不变的(比如:圆周率,性别,身份证号码,血型等等),有些值是可变的(比如:年龄,体重,薪资等等),引入了变量和常量的概念。
首先,先讲述一下变量:
语法形式为:type + name。代码如下:
int age = 150;
float weight = 45.5f; //浮点数默认为双精度浮点数,在后面加个f,说明是单精度浮点数类型
char ch = 'w';
*******************************************************************************************************
基本规则如下:
1)只能由字母(包括大写和小写),数字,下划线组成;
2)不能以数字开头;
3)长度不能超过63个字符(这纯纯抬杠,纯路人,没必要);
4)区分大写,小写;
5)变量名不能使用关键字;
6)变量的名字尽量有意义(提醒我们要了解部分英语单词)。
*******************************************************************************************************
变量分为局部变量和全局变量,当全局变量和局部变量同名时,局部变量优先。
#include
int main()
{
int num1 = 0;
int num2 = 0;
int sum = 0;
printf("请输入两个操作数:>");
scanf("%d %d", &num1, &num2);
sum = num1 + num2;
printf("sum = %d\n", sum);
return 0;
}
在vs编译时会发现,我们在这里会出现4996警告。
为什么会出现这个警告呢?是因为在vs中输入函数,人家自己有定义是scanf_s,而用scanf函数不安全。
那如何消除这个警告呢?(一共有三种方法)
首先第一种方法很简单,就是直接把scanf改成scanf_s,因为scanf_s函数是vs提供的,这样vs就不会报错了,这种方式简单快捷,但是也有不足之处,这样写出的代码没有可移植性,及直接复制粘贴后在别的编译软件上无法直接使用。那么就需要我们的第二种方法了。
第二种方法中,用#pragma warning(disable:4996)代码会让编号为4996的警告错误失效,vs就不会管你的这个代码是否正确。但是,这种方法每次创建工程后都需要进行编写,比较麻烦。
最后,第三种方法是一劳永逸的,首先,你需要在你的vs文件夹中找到这么一个叫newc++file.cpp的文件,在文件中写入#define _CRT_SECURE_NO_WARNINGS,保存关闭即可,以后每当你打开vs,新建项目的时候,第一行就会自动出现这行代码,有效解决了咱们的困扰,一劳永逸。
作用域是一个范围,其是一个程序设计概念,通常来说,一段代码中所用到的名字并不总是有效的,而限定这个名字的可用性的代码范围就是这个名字的作用域。
下面是小编对于作用域做的总结:
1)局部变量的作用域是变量所在的局部范围。
2)全局变量的作用域是整个工程。
生命周期是一个时间周期,变量的生命周期是变量的创建到变量的销毁之间的时间段。
1)局部变量的生命周期是:进入作用域生命周期开始,出作用域生命周期结束。
2)全局变量的生命周期是:整个程序的生命周期。
下面是小编对于生命周期做的总结:
如何理解程序?(这个萌新不必在意,在后面小编我会将这个内容单独拿出来讲解)
在创建一个工程中,我们可以创建多个源文件,比如用声明外部符号:"extern",可以将一个源文件定义的全局变量在另一个源文件中使用。如下图:
然后讲一下常量:
C语言中常量分为一下几种:字面常量,const修饰的常变量,#define 定义的标识符常量,枚举常量
下面小编来带着大家一一分析吧:
字面常量没有什么可以说的地方,直接写出的值;
const 修饰的常变量在C语言中只是在语法层面限制了变量不能直接被改变,但是他本质上还是一个变量,所以叫常变量。
为什么const 修饰在C语言中是常变量呢?
因为在C语言中,如果在数组中的方括号引用const 修饰的常变量,代码在编译时会出现警告,而在C++中,把const 修饰的变量看成常量。
#define定义的标识符可以在数组中使用。
枚举常量默认从0开始,依次向下递增1。
在C语言中没有字符串类型,字符串类型是可以存放在字符数组中的。
“hello world”这种由双引号引起来的一串字符称为字符串面值,或简称字符串。字符串的结束标志是一个'\0'的转义字符,在计算字符串长度的时候 \0 是结束标志,不算字符串内容。
char arr[] = "hello world";
char arr[] = {'h','e','l','l','t'}; //最后输出该数组时会出现乱码的情况
char arr[] = {'h','e','l','l','t','\0'};
定义字符串的数组中,在数组结尾需要加入 \0 来提示编译器是字符串结束标志。
转义字符顾名思义就是转变原来的意思,是为了防止一些符号写在一起时,编译器误解他们的意思。下面,我们来进行介绍几个常用的转义字符。
字符在计算机存储都有编码,ASCLL码值的取值范围是:0 - 127,后期拓展到了 0 - 255。
下面是一道经典的题目:(这个题目的答案是14)
#include
int main()
{
printf("%d\n", "c:\test\628\test.c");
return 0;
}
在这道题中,我们要小心这几个坑:1)转义字符,因为他们都在转义字符中都没有写入 '\' ,所以要将他们当做字符来看待。2)就是这个八进制的转义字符,因为会给你塞个8,但八进制中不会出现8这个数字。
这一部分还是比较简单的,在程序员中的世界中,有时候代码会进行一些冗余,代码中有些地方理解起来会比较费解,需要在旁边进行注释;有时候不需要的代码需要进行删除操作,如果不想删除,也可以进行注释。
注释有两种类型:一种是C语言风格的注释(一般都不用这个):/* */,另一种是c++风格的注释://。
if else语句在C语言中属于选择结构。
循环语句中有三种形式:while(),for(), do while()。
他们有一些区别使得他们适用的场景不太相同,如果已知循环的次数用for循环,如果不知道循环的次数用while循环,如果想要先循环一次则用do while循环。
在数学中,函数是描述变量之间的关系,在C语言中,我们用函数其实也是定义一个关系。
#include
//函数的定义和声明
int ADD(int x, int y)
{
return x + y;
}
int main()
{
int a = 0, b = 0;
int sum = 0;
scanf("%d %d", &a, &b);
//函数的调用
sum = ADD(a, b);
printf("%d\n", sum);
return 0;
}
函数的特点是简化代码,代码复用。
C语言中,数组是用来存储一组相同类型元素的集合。
数组可以初始化和不完全初始化。
完全初始化:int arr[4] = {2,3,4,5};
不完全初始化:int arr[4] = {0};
C语言规定:数组的每一个元素都有一个下标,下标是从0开始的,数组也可以通过下标来访问。
#include
int main()
{
int arr[10] = {0};
//利用循环 输入 输出
for(int i = 0; i < 10; i++)
{
scanf("%d", &arr[i]);
}
for(int i = 0; i < 10; i++)
{
printf("%d ", arr[i]);
}
printf("\n");
return 0;
}
+ - * / %
>> <<
& ^ |
= += -= *= /= ^= |= >>= <<=
! 逻辑反操作符 在C语言中,0表示假,非0表示真
sizeof 操作数的类型长度(以字节为单位) 这个最不像操作符,要记住
-- 前置--,后置-- 前置是先加1,后使用;后置是先使用,后加1
++ 前置++,后置++ 前置,后置看符号位置,自己加1,无所谓
> >= < <= != ==
&& 逻辑与 全真为真
|| 逻辑或 全假为假
在这里想起了朋友的一道题:
我刚看到这个题是有疑惑的,因为b和c选项感觉都是错的,其实并不是。因为c选项是涉及一些知识点是我不知道的,因为有逻辑短路,在C语言中,我们进行运算的时候,我们需要进行优化代码,不让这个程序进行超负荷的运算。在程序中,因为,a||(b = c)是这个逻辑运算,为什么会有逻辑短路呢?为了减少程序的计算量,在进行这个逻辑运算的时候,C语言采用了在保持原逻辑运算正确的同时,通过已确定表达式的确切值的情况下,不计算后面的运算来简化运算。
在或运算中,如果a为真,后面的值不管是什么,我们都不需要进行计算,因为程序的结果已经知道了,就应该进行逻辑短路,然后就不计算b = c,所以没有将c赋值给b, b还是等于原值。如果a为假,说明后面的结果可能会影响整个结果,所以就不能进行逻辑短路。
exp1 ? exp2 : exp3 三目操作符,如果1成立,那么输出2,否则输出3
exp1,exp2,exp3,exp4 从左向右依次计算,整个表达式的结果是最后一个表达式的值。
[ ] () . ->
这些常见关键字分为:类型,循环,分支,声明,函数等等;
类型:auto(自动),char,double,enum,float,int,long,short,signed,unsigned,union,void,sizeof,struct,typedef。
循环:break,continue,do while(),for,continue。
分支:switch,break,case,default,if else,goto。
声明:extern(声明外部变量),register,static,volatile。
函数:return。
其是一个寄存器关键字,用register声明的变量是寄存器变量,是存放在CPU的寄存器里的。寄存器变量和普通变量比起来速度上的差异很大,毕竟CPU的速度远远大于内存的速度。寄存器有这么两个特点,一个是运算速度快,一个是不能取地址。但是在寄存器中的变量是不能取地址的,编译器会报错。
typedef 顾名思义是类型定义,这里应该理解为类型重命名。目的是简化代码。
在C语言中,static是用来修饰变量和函数的。
有三个用法:
1)修饰局部变量,称为静态局部变量;
2)修饰全局变量,称为静态全局变量;
3)修饰函数,称为静态函数。
在c/c++程序中,在语言中,内存被分为三个部分:栈区,堆区,静态区。
一个普通的局部变量进入函数创建,出函数销毁,但被static修饰后,进入函数已经创建好了(因为在反汇编中,static 修饰的变量没有汇编语言。)出函数不销毁,多次调用函数=时,共享一个变量。
本质:普通局部变量放在栈区,被static修饰放在静态区中。
在C语言中,每一个.c文件单独经过编译器处理的,全局变量具有外部链接属性,这种属性决定了全局变量在多个文件之间可以使用。但被static修饰后,将全局变量的外部链接属性变成内部链接属性,使得这个全局变量只能在本文件内使用,不能在其他源文件内使用。
函数的属性和全局变量有点相似,函数也是具有外部链接属性(可以跨文件使用),一旦被static修饰,使得这个函数只能在本文件中使用,不能在其他源文件中使用。
内存是电脑中特别重要的存储器,计算机中程序的运行都是在内存中运行的。所以为了有效的使用内存,就把内存划分为一个个小小的内存单元,每一个内存单元的大小为1个字节(因为最小的数据类型为char类型,char类型的字节是1个字节),为了能够有效的访问到内存的每个单元,就给内存单元编号的,这些编号被称为该内存单元的地址。
内存和硬盘要分清楚。
32位机器中,有32个地址线,每一个地址线是0/1,也就有2的32次方个地址,能够管理4GB的内存。二进制,八进制,十进制,十六进制都是数值的表达形式。
总结:1.内存会被划分为以字节为单位的一个个内存单元;
2.每个内存单元都有编号,编号 = 地址 = 指针;
3.C语言中创建的变量,其实是向内存中申请一块空间;
4.&a时,拿出4个字节中较小的那个字节地址;
5.指针变量存储的是地址;
6.可以通过指针变量找到a。
指针变量的大小取决于地址的大小,32位机器平台下的地址是32个bit位(即4个字节),64位机器平台下的地址是64个bit位(即8个字节)。
C语言中有数组的概念,但是数组太局限,只能存储一个相同类型的数据。但现实生活中,这个数据比较复杂,仅仅用数组无法将其表达成功,所以C语言引入这个结构体来存放不同类型的数据。
如果要求结构体中某一元素,需要用该元素相对应的指针类型进行取地址。