// 单行注释
ctrl+shift+/ 块注释
其余:编辑---高级 查快捷键
4.2 变量
C语言规定,标识符可以是字母(A~Z,a~z)、数字(0~9)、下划线_组成的字符串,并且第一个字符必须是字母或下划线。还可以是$或_(不能是数字)
- 变量就是可以变化的量,每个变量都会有一个名字,叫变量名,变量名一般用标志符表示。(通俗说法)
- 在计算机程序中,变量是用来存储数据的一个内存区域,并用一个名字来表示这个区域。(标准说法)
特点:
- 变量在使用前必须先定义,定义变量前必须有相应的数据类型;
- 在程序运行过程中,其值可以改变;
#include<stdio.h>
extern int kk;//在外部声明了一个变量 ,不是定义 kk可以在别的文件中定义
extern int kk1;
int main(int num) {
//变量 可以变化的量
int a;//定义变量
a = 90;//赋值
int b = 90;//定义的的同时赋值
int m, n;//同时定义多个变量多个变量
m = 1;
n = 2;
printf("打印输出m的值:%d\n",m); // \n转义字符 表示换行
printf("hhhhhhhhhhhhhhhhhhhh");
fn();
return 0;
}
int kk1=200;
4.2.4 总结 注意事项
变量的声明与定义的区别:
1、定义变量是创建了变量并为其分配内存,声明没有分配内存
2、一个变量在一定的区域内只能被定义一次,声明可以有很多次
变量声明的本质:声明就是告诉编译器,这个变量已经在别的地方定义过了,这个只做基本的声明,并没有为其分配内存。
变量的声明与定义的区别:
1、定义变量是创建了变量并为其分配内存,声明没有分配内存
2、一个变量在一定的区域内只能被定义一次,声明可以有很多次
变量声明的本质:声明就是告诉编译器,这个变量已经在别的地方定义过了,这个只做基本的声明,并没有为其分配内存。
4.2.5 标志符的命名
1、只能由数字、字母、下划线组成
2、不能以数字开头
3、不能使用c语言的关键字
4、好的命名习惯要做到见名知义,如下:
(1)大驼峰命名法 每个单词首字母大写 例如:MyFirstName
(2) 小驼峰命名法 从第二个单词开始,首字母大写 例如:myFirstName
(3)下划线命名法 每个单词之间用_连接 例如:my_first_name
4.3. c语的关键字共有32个
5、c语言的数据类型
5.1、字符型 char
char表示为字符类型,用于存储单个字符,每个字符变量都是由8个bit位构成,在内存中就是1个字节
相关特性:
- 在给字符型变量赋值时,需要用一对英文半角格式的单引号(' ')把字符括起来。
- 字符变量在内存单元存储时,是将与该字符对应的ASCII码放到变量的存储单元中。
- char的本质就是一个1个字节大小的整型
(1)字符串 只占一个字节 ‘’ 多个字节 会有截断报告
(2)字符 输出 %c %d 对应的字符 及ASCII码
(3) ‘\0' '0'的区别
(4)大小写转换
//1.char字符串,用char定义的变量是字符型变量,占1个字节
char ch='a';
char ch1='1';
char ch2='1234';// 错误的,因为必须是一个字节
//printf("%d,%c", ch1, ch1);//52 4 数据显法不正常 有截断
#include<stdio.h>
int main() {
//char 字符类型 单引号括住 只能作用于一个字符 转义字符除外
//单引号的作用:1、定义字符 2、取字符的Ascll值
//注意:printf %c输出的是字符 %d输出的是ASCII值
char ch = 'a';
printf("%c\n", ch);
printf("%d\n", ch);
char ch2 = '0';
printf("%d\n", ch2);//48 是字符'0'的ASCLL值
printf("%c\n", ch2);//'0'
char ch3 = '\0';
printf("%d\n", ch3);//'\0' 计算机存的是 0
int a = 65;
printf("%c\n", a);
printf("%d\n", a);
//注意:'0'和'\0'的区别
//字符0存的是 48 '\0'存的是0
//字符的大小写转换
//'a' 97 'b' 98 'c' 99 ...... 'z' 122
// 'A' 65 'B' 66 'c' 67 ...... 'z' 90
char ch4 = 'a';
ch4 = ch4 - ('a' - 'A');//小写转大写
printf("%c\n", ch4);
char ch5 = 'A';
ch5 = ch5 + ('a' - 'A');
printf("%c\n", ch5);//大写转小写
return 0;
}
5.4、可移植类型
例如:32位平台下,int类型为4字节,其他平台可能是8字节,也可能是2字节,就会导致变量的值域不一样,导致程序运行结果有出入,所以我们会采用可移植的类型。
stdint.h和inttypes.h是C语言标准库中的头文件,主要用于提供可移植性的整数类型和宏定义。
5.4.2、inttypes.h提供了更多的整数类型和函数。
这个头文件定义了以下几种类型的整数:
- intmax_t:最大的整数类型
- uintmax_t:最大的无符号整数类型
- intptr_t:可以转换为指针的整数类型
- uintptr_t:可以转换为无符号整数的指针类型
5.5、常量
6、数值表示
数据在计算机中是以二进制形式存储的
1、负数在计算机中以补码的方式存储
2、非负数在计算机中以原码的方式存储 (原 反 补 三码合一)
3、八进制以原码存储
4、十六进制以原码存储
计算机数据的存储使用二进制补码形式存储 ,并且最高位是符号位。
正数:最高位是0
负数:最高位是1
规定1:正数的补码与反码、原码一样,称为三码合一
规则2:负数的补码与反码、原码不一样
负数的原码:把十进制转为二进制,然后最高位设1
负数的反码:在原码的基础上,最高位不变,其余位取反(0变1,1变0)
负数的补码:反码+1
6.1、进制
6.5、c语言如何表示响应的进制数
6.6、数值的存储方式
计算机底层都是存储数据都是采用二进制,但二进制也有几种,比如:原码、反码、补码。接下来我们来看看他们之间的关系的意义作用.
原码十进制数按照:除二取余、倒序排列,得到的就是原码。
- 10 -> 0000 1010
- -10 -> 1000 1010
- -1 -> 1000 0001
- 1 -> 0000 0001
问题:原码在做计算的时候会出现一些问题,比如正负数的加法运算,以及零的问题。
●正负数加法 -1 + 1 = 0
1000 0001 + 0000 0001 ---------------- 1000 0010 -> -2 ?
●正负零 +0 和 -0 十进制数字0,占了两个二进制;
0000 0000 1000 0000
补码正数的补码就是原码本身;负数的补码就是在反码的基础上+1;
● 1 -> 0000 0001 -> 0000 0001 -> 0000 0001 三码合一
●-1 -> 1000 0001 -> 1111 1110 -> 1111 1111
0000 0001 + 1111 1111 ---------------- 0000 0000 正负0: 0000 0000 1000 0000 ->1111 1111->0000 0000
补码在正负数加减法运算时没问题,也不会出现正负零占两个二进制。
但 1000 0000 不表示为负零,用来表示什么呢?计算机其实默认把8位有符号二进制 1000 0000 表示为 -128 。
7、输入输出
7.1、输出语句
- 输出:将程序的运行结果输出到控制台或终端窗口中
- printf语法格式:
- printf("输出格式符",输出项)
printf("我今年%d岁了\n",age) //%d表示整型占位符
格式化占位符:
打印格式 | 对应数据类型 | 含义 |
%c | char | 字符型,输入的数字按照ASCII码相应转换为对应的字符 |
%hd | short int | 短整数 |
%hu | unsigned short | 无符号短整数 |
%d | int | 接受整数值并将它表示为有符号的十进制整数 |
%u | unsigned int | 无符号10进制整数 |
%ld | long | 接受长整数值并将它表示为有符号的十进制整数 |
%f | float | 单精度浮点数 |
%lf | double | 双精度浮点数 |
%e,%E | double | 科学计数法表示的数,此处"e"的大小写代表在输出时用的"e"的大小写 |
%s | char * | 字符串。输出字符串中的字符直至字符串中的空字符(字符串以'\0‘结尾,这个'\0'即空字符) |
%p | void * | 以16进制形式输出指针 |
%o | unsigned int | 无符号8进制整数 |
%x,%X | unsigned int | 无符号16进制整数,x对应的是abcdef,X对应的是ABCDEF |
7.2、输入语句
- 输入:接收用户输入的数据的过程
- scanf语法格式:
- scanf("格式化字符串",&变量1,&变量2,......);
-
- 格式化字符串用于指定输入的数据类型及其格式
- 变量1、变量2等是要读入的变量的地址
注意使用scanf输入数据时,如果报如下错误:
这个错误信息提示你的代码中使用了 scanf 函数,这个函数可能存在安全问题,你可以考虑使用 scanf_s 函数来代替,以确保代码的安全性。
解决方法有两种:
1、将scanf改为scanf_s即可
2、在代码的最上行加入:#define _CRT_SECURE_NO_WARNINGS
8、运算符
8.1、算术运算符
运算符 | 术语 | 示例 | 结果 |
+ | 加 | 10 + 5 | 15 |
- | 减 | 10 - 5 | 5 |
* | 乘 | 10 * 5 | 50 |
/ | 除 | 10 / 5 | 2 |
% | 取模(取余) | 10 % 3 | 1 |
++a | 前自增 | a=2; b=++a; | a=3; b=3; |
a++ | 后自增 | a=2; b=a++; | a=3; b=2; |
--a | 前自减 | a=2; b=--a; | a=1; b=1; |
a-- | 后自减 | a=2; b=a--; | a=1; b=2; |
8.2、赋值运算符
运算符 | 术语 | 示例 | 结果 |
= | 赋值 | a=2; b=3; | a=2; b=3; |
+= | 加等于 | a=0; a+=2; 等同于 a = a + 2; | a=2; |
-= | 减等于 | a=5; a-=3; 等同于 a = a - 3; | a=2; |
*= | 乘等于 | a=2; a*=2; 等同于 a = a * 2; | a=4; |
/= | 除等于 | a=4; a/=2; 等同于 a = a / 2; | a=2; |
%= | 模等于 | a=3; a%=2; 等同于 a = a % 2; | a=1; |
8.3、比较运算符
C 语言的比较运算中, “真”用数字“1”来表示, “假”用数字“0”来表示。
运算符 | 术语 | 示例 | 结果 |
== | 相等于 | 4 == 3 | 0 |
!= | 不等于 | 4 != 3 | 1 |
< | 小于 | 4 < 3 | 0 |
> | 大于 | 4 > 3 | 1 |
<= | 小于等于 | 4<=3 | 0 |
>= | 大于等于 | 4 >= 1 | 1 |
8.4、逻辑运算符
运算符 | 术语 | 示例 | 结果 |
! | 非 | !a | 如果a为假,则!a为真; 如果a为真,则!a为假。 |
&& | 与 | a && b | 如果a和b都为真,则结果为真,否则为假。 |
|| | 或 | a || b | 如果a和b有一个为真,则结果为真,二者都为假时,结果为假。 |
8.5、位运算符
8.5.1、按位与(&)运算:位与位进行比较,如果都为1,则为1,否则为0;(一假则假)
8.5.2、按位或(|)运算:位与位进行比较,如果都为0,则为0,否则为1;(一真则真)
8.5.3、按位异或运算:位与位进行比较,相同为0,不同为1;(不同为真)
8.5.4、按位取反运算:补码取反,再将取反后的补码转为原码;
ps:无符号的数据,取反后最高位为1,也不需要逆运算。
- 对于无符号数据,取反就是简单的按位取反,取反后的值是一个有效的无符号数,且不需要通过逆运算来恢复原始值。
8.5.5、左移运算符
将数字的二进制补码全部向左移动,空出来的位置补0,超出范围的二进制数丢弃;
有符号的数据左移后最高位如果为1,则需要进行逆运算;
注意事项:
- 无符号的数据,左移后最高位为1,也不需要逆运算;
- -128:1000 0000 特殊情况也不需要逆运算;
1.位运算符针对是整型数值做的运算
2.运算规则:在一定范围转内,数据每向左移动一位,相当于原数据*2 (正数、负数都适用)
如果在8位单片机下 就不太适合
8.5.6、右移运算符 >>
逻辑移位:将数字的二进制补码全部向右移动,空出来的位置补0,超出范围的二进制数丢弃
算术移位:左边移入的位由原先该值的符号位决定,符号位为1,则移入的位均为1,符号位为0,则移入的位均为0,这样能保证原数的正负形式不变
标准规定,无符号值执行的所有位移操作都是逻辑移位,对于有符号值,到底采用逻辑移位还是算术移位取决于编译器。
运算规则:在一定范转内,数据每向右移动一位,相当于原数据/2 (正数、负数都适用)
注意:
1. 如果不能整除,向下取整
2.右移运算符最好只用于无符号整数,不要用于负数。因为不同系统对于右移后如何处理负数的符号位方法,可能会得到不一样的结构
不考虑平台的影响适用, 如果在8位单片机下 就不太适合
5.5.7、运算符的优先级
- 不同的运算符默认具备不同的优先级,符号较多不用记,现用现查就可以。
- 当无法确定谁的优先级高时,加一个小括号就解决了。
优先级 | 运算符 | 名称或含义 | 使用形式 | 结合方向 | 说明 |
1 | [] | 数组下标 | 数组名[常量表达式] | 左到右 | -- |
() | 圆括号 | (表达式)/函数名(形参表) | -- | ||
. | 成员选择(对象) | 对象.成员名 | -- | ||
-> | 成员选择(指针) | 对象指针->成员名 | -- | ||
2 | - | 负号运算符 | -表达式 | 右到左 | 单目运算符 |
~ | 按位取反运算符 | ~表达式 | |||
++ | 自增运算符 | ++变量名/变量名++ | |||
-- | 自减运算符 | --变量名/变量名-- | |||
* | 取值运算符 | *指针变量 | |||
& | 取地址运算符 | &变量名 | |||
! | 逻辑非运算符 | !表达式 | |||
(类型) | 强制类型转换 | (数据类型)表达式 | -- | ||
sizeof | 长度运算符 | sizeof(表达式) | -- | ||
3 | / | 除 | 表达式/表达式 | 左到右 | 双目运算符 |
* | 乘 | 表达式*表达式 | |||
% | 余数(取模) | 整型表达式%整型表达式 | |||
4 | + | 加 | 表达式+表达式 | 左到右 | 双目运算符 |
- | 减 | 表达式-表达式 | |||
5 | 左移 | 变量 | 左到右 | 双目运算符 | |
>> | 右移 | 变量>>表达式 | |||
6 | > | 大于 | 表达式>表达式 | 左到右 | 双目运算符 |
>= | 大于等于 | 表达式>=表达式 | |||
小于 | 表达式 | ||||
小于等于 | 表达式 | ||||
7 | == | 等于 | 表达式==表达式 | 左到右 | 双目运算符 |
!= | 不等于 | 表达式!= 表达式 | |||
8 | & | 按位与 | 表达式&表达式 | 左到右 | 双目运算符 |
9 | ^ | 按位异或 | 表达式^表达式 | 左到右 | 双目运算符 |
10 | | | 按位或 | 表达式|表达式 | 左到右 | 双目运算符 |
11 | && | 逻辑与 | 表达式&&表达式 | 左到右 | 双目运算符 |
12 | || | 逻辑或 | 表达式||表达式 | 左到右 | 双目运算符 |
13 | ?: | 条件运算符 | 表达式1? 表达式2: 表达式3 | 右到左 | 三目运算符 |
14 | = | 赋值运算符 | 变量=表达式 | 右到左 | -- |
/= | 除后赋值 | 变量/=表达式 | -- | ||
*= | 乘后赋值 | 变量*=表达式 | -- | ||
%= | 取模后赋值 | 变量%=表达式 | -- | ||
+= | 加后赋值 | 变量+=表达式 | -- | ||
-= | 减后赋值 | 变量-=表达式 | -- | ||
左移后赋值 | 变量 | -- | |||
>>= | 右移后赋值 | 变量>>=表达式 | -- | ||
&= | 按位与后赋值 | 变量&=表达式 | -- | ||
^= | 按位异或后赋值 | 变量^=表达式 | -- | ||
|= | 按位或后赋值 | 变量|=表达式 | -- | ||
15 | , | 逗号运算符 | 表达式,表达式,… | 左到右 | -- |