版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、单片机原理及应用(第 4 章 单片机Cx51编程基础)教学内容编程语言简介数制与编码Cx51变量和运算符Cx51函数Cx51流程控制语句Cx51数组Cx51指针Cx51 预处理Keil C51集成开发环境DATE: 2022/7/17PAGE: 2 一、编程语言简介机器语言是用二进制代码表示的,能被计算机直接识别和执行的一种机器指令的集合。直观性和通用性都很差汇编语言采用了助记符号编写程序,通过编译器转换成能够被计算机识别和处理的二进制代码程序。汇编语言仍然是面向机器的语言,编程烦琐费时,通用性也差。高级语言用与自然语言接近的代码编写程序,通过编译器转换成二进制代码程序。高级语言易学易用,通用
2、性好。 C语言是一种结构化的高级编程语言,在单片机系统开发中得到了广泛应用。DATE: 2022/7/17PAGE: 3 二、数制与编码1.数制的基与权基:各计数制中每个数位上可用字符的个数。权:数字“1”在数字不同的数位所代表的数值。二进制基数为2( 0和1),权为以2为底的幂。二进制数字后面用B表示十进制基数为10(0-9),权是以10为底的幂。十进制用D(或不加标志)表示十进制数十六进制 基数为16(0-9以及A-F),权是以16为底的幂。十六进制用H表示十六进制数DATE: 2022/7/17PAGE: 4 二、数制与编码1.数制的基与权例1:若数字1001.01分别为二进制、十进制数
3、和十六进制数,则权值分别为:二进制数1001.11从左到右各位的权分别是23、22、21、20、2-1和2-2,即8、4、2、1、0.5、和0.25。十进制数1001.01从左到右各位的权分别是103、102、101、100、10-1和10-2,即1000、100、10、1、0.1、和0.01。十六进制数1001.01从左到右各位的权分别是163、162、161、160、16-1和16-2,即4096、256、16、1、0.0625、和0.00390625。DATE: 2022/7/17PAGE: 5 二、数制与编码2.各种数制之间的相互转换非十进制数转换为十进制数 方法:将系数与对应的权值相
4、乘并求和,所得结果即为该数对应的十进制数。例2:将二进制数110.11转换为十进制数解 110.11B=122+121+020+12-1+12-2 = 4+2+0.5+0.25 =6.75DATE: 2022/7/17PAGE: 6 二、数制与编码2.各种数制之间的相互转换非十进制数转换为十进制数例3: 将十六进制数121D.2转换为十进制数 解 121D.2H =1163+2162+1161+13160+216-1 = 4096+192+16+13+0.125 =4317.125DATE: 2022/7/17PAGE: 7 二、数制与编码十进制数转换为非十进制数对于整数部分采用“除基取余,先
5、低后高”的方法,对小数部分采用“乘基取整,先高后低”的方法,可将十进制数转换为非十进制数。 例4:将50.75转换为二进制数 因此可得:50.75=110010.11BDATE: 2022/7/17PAGE: 8 二、数制与编码例5 将十进制数500.03125转换为十六进制数 解 : 因此可得: 500.03125=1F4.08HDATE: 2022/7/17PAGE: 9 二、数制与编码十六进制数与二进制数之间的转换整数部分由小数点向左每4位一组,若整数最高位的一组不足4位,则在其左边加0补足4位;小数部分由小数点向右每4位一组,若小数最低位的一组不足4位,则在其右边加0补足4位;用与每组
6、二进制数所对应的十六进制数取代每组的4位二进制数即可转换为十六进制。将十六进制数转换为二进制数时,过程相反。 DATE: 2022/7/17PAGE: 10 二、数制与编码十六进制数与二进制数之间的转换例6:将十六进制数9F4.1H转换为二进制数解 将每位十六进制数写为二进制数 9 F 4 . 1 1001 1111 0100 . 0001 可得: 9F4.1H = 100111110100.0001BDATE: 2022/7/17PAGE: 11 二、数制与编码编码是计算机为输入处理字母、数字和符号等组成的信息,依靠输入设备先把要输入的字符按一定格式编成的二进制代码。目前国际上使用的字符编码
7、是ASCII码(American standard coded for information interchange,美国信息交换标准码)。ASCII码用一个字节来表示一个字符,采用7位二进制代码来对字符进行编码,最高位一般用做校验位,因此共128个,包括32个通用控制符号、10个阿拉伯数字、52个英文大写和小写字母及34个专用符号。数字0-9的ASCII码为30H-39H,英文大写字母A-Z的ASCII码为41H-5AHDATE: 2022/7/17PAGE: 12 三、Cx51变量和运算符数据可分为常量和变量。常量是数值和字符等不能改变的量,可以不经说明和定义直接使用,而变量是在程序运行
8、过程中可以根据需要改变的量,在引用之前必须定义类型。C51 定义一个变量的格式如下: 数据类型 存储类型 变量名表 其中“数据类型”和“存储类型”的先后次序可以互换。DATE: 2022/7/17PAGE: 13 三、Cx51变量和运算符-数据类型 表4-1 Cx51支持的数据类型DATE: 2022/7/17PAGE: 14 三、Cx51变量和运算符-数据类型bit 、 sfr 、 sfr16 和 sbit是 Keil C51中新增的变量类型。(1)bit用来定义位变量,值只能是0或1。位变量位于8051单片机内部RAM位寻址区(20H2FH),共为16字节,最多可定义128个位变量。DAT
9、E: 2022/7/17PAGE: 15 三、Cx51变量和运算符-数据类型(2)sfr用于定义特殊功能寄存器变量。该变量存储在片内的特殊功能寄存器存储区中,用来对特殊功能寄存器进行读写操作。 例如:51头文件中有定义sfr P0=0 x90,这一语句定义了P0端口在片内的寄存器,在程序中可以使用P0对该端口寄存器进行操作。DATE: 2022/7/17PAGE: 16 二、Cx51变量和运算符-数据类型(3)sfr16也用于定义特殊功能寄存器,所不同的是它用于操作占两个字节的特殊功能寄存器。 例如:sfr16 DPTR=0 x82语句定义了片内16位数据指针寄存器DPTR,其低8位字节地址为
10、82H,高8位字节地址为83H,在程序中可以对DPTR进行操作。DATE: 2022/7/17PAGE: 17 三、Cx51变量和运算符-数据类型(4)sbit用于定义特殊功能寄存器位变量,用来对特殊功能寄存器的可位寻址位进行读写操作。 例如sbit P0_0=P00 定义了特殊功能寄存器P0的第0位,后面对该位的操作可用P0_0代替。符号后面的数字定义特殊功能寄存器可寻址位在寄存器中的位置,取值必须是0-7。DATE: 2022/7/17PAGE: 18 三、Cx51变量和运算符-存储类型表4-2 Cx51存储类型DATE: 2022/7/17PAGE: 19 三、Cx51变量和运算符-存储
11、类型1.片内存储区(1)data将变量存储在片内可直接寻址的数据存储器DATA区中。DATA区位于片内RAM的低128字节(0X000X7F)。使用data存储模式,目标代码中对变量的访问速度最快,把经常使用的变量放在DATA区可提高程序运行速度。若定义i为存储类型为data的无符号字符型数据,可声明为: unsigned char data iDATE: 2022/7/17PAGE: 20 三、Cx51变量和运算符-存储类型(2) bdata用于将变量定义在数据存储器可位寻址的BDATA区,允许位与字节混合访问。BDATA区位于单片机内部RAM字节地址0 x200 x2F的16个字节中,每个
12、字节8位,共计16x8=128个可寻址位。例如如下声明后可用位变量value0访问字节value的0位: unsigned char bdata value; bit value0=value0; 若value的原值为0 x00,欲将value的第0位置为1,可采用按字节访问方式“value=0 x01”实现,也可以按位寻址方式“value0=1”实现。DATE: 2022/7/17PAGE: 21 三、Cx51变量和运算符-存储类型idata将变量存储在片内间接寻址的数据存储区IDATA区中。IDATA区使用指针来进行寻址和访问。51内核单片机RAM仅有128个字节,因此无间接寻址数据存储器
13、区,idata与data无区别。52内核单片机RAM有256个字节,当片内128字节的直接寻址数据存储区不够用时,可以使用128字节间接寻址数据存储区,访问速度较data慢一些。DATE: 2022/7/17PAGE: 22 三、Cx51变量和运算符-存储类型2.片外存储区xdata将变量存储在片外数据存储器中,采用16位地址,可以访问外部数据存储区64KB内的任何地址。pdata将变量存储在片外数据存储器中的第一页(地址00HFFH)中,存储空间为256字节。对PDATA区寻址,只需要装入8位地址,而对XDATA区寻址要装入16位地址,因此对PDATA区的寻址要比对XDATA区寻址快。pda
14、ta和xdata存储类型的变量由于需要访问外存,访问速度最慢,应尽量减少对变量的访问次数。这两种类型适合保存原始数据或最终结果,需要频繁访问的中间结果应尽量不用或少用。DATE: 2022/7/17PAGE: 23 三、Cx51变量和运算符-存储类型3.程序存储器ROMcode将变量存储在程序存储器中,变量只能读不能写,因此适合存储常量或查表类的数组数据,不能用于存储程序运行过程中需要修改的变量。如果想改变变量值,只能在程序中修改后重新将程序烧写进ROM中。DATE: 2022/7/17PAGE: 24 三、Cx51变量和运算符-运算符表4-3 Cx51中的算术运算符DATE: 2022/7/
15、17PAGE: 25 三、Cx51变量和运算符-运算符表4-4 Cx51中的关系运算符DATE: 2022/7/17PAGE: 26 三、Cx51变量和运算符-运算符表4-5 Cx51中的逻辑运算符DATE: 2022/7/17PAGE: 27 三、Cx51变量和运算符-运算符表4-6 Cx51中的位运算符DATE: 2022/7/17PAGE: 28 三、Cx51变量和运算符-运算符表4-7 Cx51中的复合运算符DATE: 2022/7/17PAGE: 29 四、Cx51函数 函数可分为主函数、标准库函数、自定义函数三类。1、主函数Cx51语言程序中有且只能有一个主函数main()。一个C
16、x51语言程序的执行从主函数开始,主函数可以调用其它函数,包括库函数和自定义函数,其它函数不能调用主函数。主函数的标准写法是 int main( void ) 前面的int是main 函数的返回值类型,用于向操作系统说明程序的退出状态,返回0代表正常退出,1代表异常。形式参数“void”用于说明主函没有输入参数。DATE: 2022/7/17PAGE: 30 四、Cx51函数 2、库函数 Cx51编译器提供了丰富的库函数,库函数是已经编写好的功能函数,可完成数学计算、输入输出等常用功能,供开发人员调用,以提高编程效率。 如果程序中使用了库函数,则应该在程序的开头处使用#include包含语句,
17、将所用的函数头文件包含到程序中来。DATE: 2022/7/17PAGE: 31 四、Cx51函数 3、自定义函数可根据需要编写自定义功能函数,结构如下:返回值类型 函数名(类型 形参) 数据定义; 执行语句; 返回值;DATE: 2022/7/17PAGE: 32 四、Cx51函数 形参和返回值是函数与外界联系的桥梁。形参是在函数调用时由外界传入函数体内的参数,形参可以没有,也可以有多个;返回值是函数运行完毕时返回给调用该函数语句的值。如果函数没有返回值,那么应声明为void类型,凡不加返回值类型限定的函数,就会被编译器作为返回整型值处理。根据作用范围的不同,变量可分为局部变量和全局变量。局
18、部变量是定义在函数内部的变量,只在该函数内部有效;全局变量是定义在函数外部的变量,从其定义位置开始到源文件结束都有效。如果全局变量和某一函数的局部变量同名,则在该函数内部只有局部变量有效。DATE: 2022/7/17PAGE: 33 四、Cx51函数 DATE: 2022/7/17PAGE: 34 例7 左图是8051单片机的P1.0口上连接了一个LED,请编程实现LED周期闪烁。四、Cx51函数 #include /包含单片机定义寄存器的头文件 sbit led = P10; /将led定义为P1.0位void delay(void) /延时函数 unsigned int i; /定义无符
19、号整数,最大取值范围65535 for(i=0;i20000;i+);/做20000次空循环,以进行延时。 int main(void ) /主函数 while(1) /无限循环,以使LED持续闪烁。 led =0; / P1.0输出低电平,灯亮 delay(); /延时一段时间 led =1; / P1.0输出高电平,灯灭 delay(); /延时一段时间 DATE: 2022/7/17PAGE: 35 四、Cx51函数 例8 下图是8051单片机的P0口上连接了8个LED,请采用移位操作编写程序实现LED流水灯。DATE: 2022/7/17PAGE: 36 四、Cx51函数 #inclu
20、de /包含单片机定义寄存器的头文件void delay(void) /延时函数 unsigned int i; /定义无符号整数,最大取值范围65535 for(i=0;i7; /将led最高位先放到a中的最低位中,a中其它位全为0b = led1; /将led左移一位,最低位补零led = b|a; /位或运算 delay(); DATE: 2022/7/17PAGE: 37 五、流程控制语句-顺序结构Cx51流程控制共有3种基本结构:顺序结构、选择结构以及循环结构。1.顺序结构 顺序结构是最基本、最简单的编程结构,程序按先后顺序执行指令代码。DATE: 2022/7/17PAGE: 38
21、 五、流程控制语句-顺序结构例 9:下图是8051单片机的P0口和P1口上分别连接了8个LED,请分别用P0和P1口显示加法125+34和减法176-98的运算结果DATE: 2022/7/17PAGE: 39 五、流程控制语句-顺序结构#includeint main(void) unsigned char a=125,b=34,c=176,d=98; P1=a+b; /加法运算结果送P1端口,P1=159=1001 1111B P0=c-d; /减法运算结果送P0端口,P0=78=0100 1110B while(1); /循环等待,防止主程序退出后单片机跑飞 DATE: 2022/7/1
22、7PAGE: 40 五、流程控制语句-选择结构2.选择结构(1)if语句 if语句用于根据条件判定结果决定执行的语句。if语句有三种基本形式:if(表达式) 语句组 说明:如果“表达式”为真,则执行花括号中的语句组,否则跳过花括号执行下面的语句。if(表达式) 语句组1 else 语句组2 说明:如果“表达式”真,则执行语句组1,否则执行语句组2。DATE: 2022/7/17PAGE: 41 五、流程控制语句-选择结构if(表达式1) 语句1 else if(表达式2) 语句组2 else if(表达式3) 语句组3 else if(表达式m) 语句组m else 语句组n 说明:如果“表达
23、式1”为真,则执行“语句组1”,否则如果“表达式2”为真,则执行“语句组2”,如果所有的表达式都不满足,则执行语句组n。DATE: 2022/7/17PAGE: 42 五、流程控制语句-选择结构例10:同图4-2,用if语句根据54/18的计算结果选择P0口8位LED的状态.DATE: 2022/7/17PAGE: 43 五、流程控制语句-选择结构#include /包含单片机寄存器的头文件int main(void) unsigned char a=54,b=18; if (a/b=1)P0=0 xfe; /第一个LED亮 else if (a/b=2) P0=0 xfd; /第二个LED亮
24、 else if (a/b=3) P0=0 xfb; /第三个LED亮 else if (a/b=4) P0=0 xf7; /第四个LED亮 else if (a/b=5) P0=0 xef; /第五个LED亮 else if (a/b=6) P0=0 xdf; /第八个LED亮 else if (a/b=7) P0=0 xbf; /第七个LED亮 else if (a/b=8) P0=0 x7f; /第八个LED亮 else P0=0 xff; /缺省值,关闭所有LED while(1); DATE: 2022/7/17PAGE: 44 五、流程控制语句-选择结构(2)switch/case
25、语句 根据表达式的值决定要执行的语句组,用于实现多中选一,形式如下: switch(表达式) case常量表达式1:/如果1满足,则执行语句组1 语句组1; break; /跳出switch结构case常量表达式2:/如果2满足,则执行语句组2 语句组2; break; /跳出switch结构default: /条件都不满足时,执行语句组n 语句组n; DATE: 2022/7/17PAGE: 45 五、流程控制语句-选择结构例 11:同图4-2,用swtich语句根据54/18的计算结果选择P0口8位LED的状态DATE: 2022/7/17PAGE: 46 五、流程控制语句-选择结构#in
26、clude /包含单片机寄存器的头文件int main(void) unsigned char a=56,b=18; switch(a/b) /使用多分支选择语句 case 1: P0=0 xfe; break; /第一个LED亮 case 2: P0=0 xfd; break; /第二个LED亮 case 3: P0=0 xfb; break; /第三个LED亮 case 4: P0=0 xf7; break; /第四个LED亮 case 5: P0=0 xef; break; /第五个LED亮 case 6:P0=0 xdf; break; /第六个LED亮 case 7:P0=0 xbf
27、; break; /第七个LED亮 case 8:P0=0 x7f; break; /第八个LED亮 default: P0=0 xff; /缺省值,关闭所有LED while(1);DATE: 2022/7/17PAGE: 47 五、流程控制语句-循环结构1、for循环 for 循环结构用于按指定的次数循环执行一组语句,格式如下:for(表达式1;表达式2;表达式3)语句;for循环语句执行过程如下:(1)先执行表达式1,一般是对循环变量赋初值;(2)执行表达式2,若表达式2结果为真,则执行循环体语句,并求解表达式3(一般是改变循环变量的值); 然后再次执行表达式2;并判断结果真假(3)若表
28、达式2结果为假,则退出for循环。DATE: 2022/7/17PAGE: 48 五、流程控制语句-循环结构例 12:同图4-3,用for循环计算7的阶乘并送P1和P0口显示结果。DATE: 2022/7/17PAGE: 49 五、流程控制语句-循环结构#include /包含单片机寄存器的头文件int main(void) unsigned char i; unsigned int s=1; for(i=1;i=7;i+) s=s*i; /计算阶乘 P1=s/256; /高8位送P1显示 P0=s%256; /低8位送P0显示 while(1);DATE: 2022/7/17PAGE: 50
29、 五、流程控制语句-循环结构(3)while循环 while循环语句先判断条件真假,若表达式为真,则执行花括号内的语句组,否则终止循环,格式如下: while(表达式) 语句组DATE: 2022/7/17PAGE: 51 五、流程控制语句-循环结构例 13:同图4-3,用while循环计算7的阶乘并送P1和P0口显示结果。DATE: 2022/7/17PAGE: 52 五、流程控制语句-循环结构#include /包含单片机寄存器的头文件int main(void) unsigned char i=1; unsigned int s=1; while(i=7) s=s*i; /计算阶乘 i+
30、; /i自增运算 P1=s/256; /高8位送P1显示 P0=s%256; /低8位送P0显示 while(1);DATE: 2022/7/17PAGE: 53 五、流程控制语句-循环结构(4) do while 循环 先执行花括号内的语句组,然后执行表达式,若结果为真,则重复执行花括号内的语句组,否则终止循环,格式如下:do 语句组while(表达式);DATE: 2022/7/17PAGE: 54 五、流程控制语句-循环结构例14:根据下图用do while循环计算7的阶乘并送P1和P0口显示结果。DATE: 2022/7/17PAGE: 55 五、流程控制语句-循环结构#include
31、 /包含单片机寄存器的头文件int main(void) unsigned char i=1; unsigned int s=1; do s=s*i; /计算阶乘 i+; /i自增运算 while(i=7); P1=s/256; /高8位送P1显示 P0=s%256; /低8位送P0显示 while(1);DATE: 2022/7/17PAGE: 56 六、Cx51数组-一维数组1.一维数组 (1)一维数组的定义方式为: 数据类型 数组名 常量表达式;例如定义有3个元素字符型数组m:char m3; m的3个元素分别是m0, m1, m2。数组的类型指数组元素的取值类型。对于同一个数组,其所有
32、元素的数据类型都是相同的。DATE: 2022/7/17PAGE: 57 六、Cx51数组-一维数组(2)一维数组的初始化 数组初始化是指在数组定义时给数组元素赋予初值。例如: int m3= 0,1,2;相当于a0=0,a1=1,a2=2。当 中值的个数少于元素个数时,只给前面部分元素赋值,其他元素自动赋0值。例如: int m3=0,1结果是a0=0,a1=1,a2=0。DATE: 2022/7/17PAGE: 58 六、Cx51数组-一维数组(3)一维数组元素的引用 数组必须预先定义才能使用。数组只能逐个地使用各元素,而不能一次引用整个数组。例如,输出有10个元素的数组必须使用循环语句逐
33、个输出各下标变量: for(i=0; i3; i+) printf(%d,mi);而不能用一个语句输出整个数组。因此,下面的写法是错误的: printf(%d,m);DATE: 2022/7/17PAGE: 59 六、Cx51数组-一维数组例 15:用一维数组实现流水点亮P0口的8位LEDDATE: 2022/7/17PAGE: 60 六、Cx51数组-一维数组int main(void) /主函数 unsigned char i; unsigned char code Tab =0 xfe,0 xfd,0 xfb,0 xf7,0 xef,0 xdf,0 xbf,0 x7f; /定义无符号字符
34、型数组 while(1) for(i=0;i8;i+) P0=Tabi;/依次引用数组元素,并将其送P0口显示 delay();/调用延时函数 DATE: 2022/7/17PAGE: 61 六、Cx51数组-二维数组2.二维数组 二维数组是以行列矩阵的形式存储数据。 (1)二维数组定义 数据类型 数组名下标1下标2; 第一个下标代表行,第二个下标代表列。例如语句 int a23 定义了二维整形数组,共有2行3列6个元素。DATE: 2022/7/17PAGE: 62 六、Cx51数组-二维数组 (2)二维数组的初始化 可以采用以下两种方式初始化: 按先行后列的存储顺序整体赋值,例如: int
35、 a23=0,1,2,3,4,5 按每行分别赋值,例如: int a23=0,1,2,3,4,5;DATE: 2022/7/17PAGE: 63 六、Cx51数组-二维数组例 16:用二维数组实现流水点亮P0口的8位LED。DATE: 2022/7/17PAGE: 64 六、Cx51数组-二维数组int main(void) unsigned char i,j; unsigned char code Tab24=0 xfe,0 xfd,0 xfb,0 xf7,0 xef,0 xdf,0 xbf,0 x7f; /定义无符 /号字符型数组 while(1) for(i=0;i2;i+) for(j
36、=0;j4;j+) P0=Tabij;/依次引用数组元素,并将其送P0口显示 delay();/调用延时函数 DATE: 2022/7/17PAGE: 65 六、Cx51指针变量的指针就是变量的地址。在C语言中,允许用一个变量来存放指针,这种变量称为指针变量。指针变量是一种特殊的变量,它也和一般变量一样,具有变量名、类型和值,但它的值就是变量所存放的地址。通过指针对变量进行操作是间接操作,比直接操作变量更费时间,且不够直观,但可以通过灵活运用指针使程序代码更为简洁、有效。DATE: 2022/7/17PAGE: 66 六、Cx51指针1、指针变量的定义 指针变量同普通变量一样,使用之前要进行定
37、义。指针变量定义的一般形式为: 数据类型 *变量名; 其中,数据类型表示本指针变量所指向变量的数据类型,*表示这是一个指针变量。 例如: 定义:int *point,表示point指向一个整型变量,但point具体指向哪一个整型变量,取决于point中所存储的地址。一个指针变量只能指向同类型的变量,如上述point 只能指向整形变量,不能指向一个字符变量。DATE: 2022/7/17PAGE: 67 六、Cx51指针2、指针变量的引用 指针变量在使用之前必须赋予具体的地址,使用未经赋值的指针变量会引起严重后果。指针变量的引用有两个重要运算符: &:取地址运算符; *:指针运算符(或称“间接访
38、问” 运算符)。 在指针变量定义中所出现的“*”是类型说明符,表示其后的变量是指针类型,而指针运算符“*”则出现在表达式中,用以表示指针指向的变量值。DATE: 2022/7/17PAGE: 68 六、Cx51指针地址运算符&用来取出变量的地址。其形式为: &变量名;指针运算符*用来取出指针指向变量的值,其形式为: *指针变量名;例如语句:point = &i;j= *point; 表示取出变量i的值赋予变量j,与语句j=i的效果相同。对*point的任何操作与直接对变量i的操作效果相同。DATE: 2022/7/17PAGE: 69 六、Cx51指针3、数组指针一个变量有一个地址,一个数组包
39、含若干元素,每个数组元素都在内存中占用存储单元,它们都有相应的地址。数组的指针是指数组的起始地址,数组元素的指针是数组元素的地址。一个数组是由连续的一块内存单元组成的。数组名就是这块连续内存单元的首地址。一个数组也是由各个数组元素(下标变量)组成的。每个数组元素按其类型不同占有几个连续的内存单元。一个数组元素的首地址也是指它所占有的几个内存单元的首地址。DATE: 2022/7/17PAGE: 70 六、Cx51指针定义一个指向数组元素的指针变量,与定义普通变量的指针相同。例如:int m=1,2,3;int *p;p=&m0; 经上述定义后,p就是数组m的指针。因为数组名代表数组的首地址,也
40、就是第一个元素的地址,因此下面两个语句等价:p=&m0;p=m;p指向数组m的首地址后,p+i就是数组的元素mi。DATE: 2022/7/17PAGE: 71 六、Cx51指针例 17:用一维数组实现流水点亮P0口的8位LED。 DATE: 2022/7/17PAGE: 72 六、Cx51指针int main(void) unsigned char i; unsigned char code Tab8=0 xfe,0 xfd,0 xfb,0 xf7,0 xef,0 xdf,0 xbf,0 x7f; /*定义无符号字符型数组*/ unsigned char *p=&Tab0;/*定义指针变量并
41、指向Tab数组,也可写为unsigned char *p=Tab */ while(1) for(i=0;i8;i+) P0=*(p+i);/通过指针变量依次引用数组元素,并将其送P0口显示 delay();/调用延时函数 DATE: 2022/7/17PAGE: 73 六、Cx51指针指向二维数组的指针变量的说明形式为类型说明符 (*指针变量名)长度;“长度”是二维数组的列数。二维数组的每一行都代表一个一维数组,该一维数组的长度就是二维数组的列数。若该指针变量指向二组数组Amn的首地址,则 *(指针变量名+i)就是Ai,而Ai是一维数组Ain的首地址,*(*(指针变量名+i)+j)就是Aij
42、的值。DATE: 2022/7/17PAGE: 74 六、Cx51指针例 18:用二维数组实现流水点亮P0口的8位LED。 DATE: 2022/7/17PAGE: 75 六、Cx51指针int main(void) unsigned char i,j; unsigned char code Tab24=0 xfe,0 xfd,0 xfb,0 xf7,0 xef,0 xdf,0 xbf,0 x7f; /定 /义无符号字符型数组 unsigned char (*p)4; /定义二维数组指针 p=Tab;/指向二维数组首地址 while(1) for(i=0;i2;i+) for(j=0;j4;j
43、+) P0=*(*(p+i)+j);/依次引用数组元素,并将其送P0口显示 delay();/调用延时函数 DATE: 2022/7/17PAGE: 76 七、Cx51 预处理预处理部分放源程序的前面,以“#”号开头,包含命令#include、宏定义命令#define等。编译器在对程序进行编译前,首先对源程序中的预处理部分进行处理,然后才对源程序进行编译。合理地使用预处理功能编写的程序更简洁,便于维护和修改,有利于模块化程序设计。C语言提供了多种预处理功能,如文件包含、宏定义以及条件编译等。DATE: 2022/7/17PAGE: 77 七、Cx51 预处理-文件包含1、文件包含文件包含是把指
44、定文件的内容全部插入该命令行位置,从而把指定的文件和当前的源程序文件连成一个源文件。文件包含命令行的一般形式为: #include 或 #include 文件名使用尖括号表示在用户系统环境设置的包含目录中查找;使用双引号则首先在当前的源文件目录中查找,若未到才到包含目录中去查找。DATE: 2022/7/17PAGE: 78 七、Cx51 预处理-宏定义2、宏定义宏定义是指用一个标识符来表示一个字符串。在编译预处理时,对程序中所有出现的宏标识符,都用宏定义中的字符串去代换,称为宏代换。字符串中可以含任何字符,可以是常数,也可以是表达式,预处理程序对它不作任何检查,如有错误也只能在程序编译时发现
45、。宏定义不是实际程序语句,在行末不必加分号,如加上分号则连分号也一起置换。宏定义可以有参数也可以无参数。DATE: 2022/7/17PAGE: 79 七、Cx51 预处理-宏定义(1)无参数宏定义 无参数宏的宏名后不带参数。其定义的一般形式为: #define 标识符 字符串 其中“字符串”可以是常数、表达式、格式串等。 例如: 宏定义 “ #define AREA 3.14*r*r”的作用是指定标识符AREA 来代替计算圆面积的表达式3.14*r*r。在编写程序时,用到计算圆面积都可由宏名AREA代替,当程序编译时,编程器将首先进行宏代换,即用表达式3.14*r*r去置换所有的宏名AREA
46、,然后再进行编译。DATE: 2022/7/17PAGE: 80 七、Cx51 预处理-宏定义(2)带参数宏定义 对带参数的宏不仅要宏代换,而且要用实际的值替换参数。带参宏定义的一般形式为: #define 宏名(参数表) 字符串 带参宏调用的一般形式为: 宏名(实际参数值); 例如: 宏定义“#define AREA(r) 3.14*r*r”在程序中调用时需要给出半径r具体值:area= AREA(4) 在宏调用时,用实际半径值4去代替参数r,经宏代换后的语句为: area=3.14*4*4DATE: 2022/7/17PAGE: 81 七、Cx51 预处理-条件编译3、条件编译条件编译可以
47、按不同的条件去编译不同的程序部分,因而产生不同的目标代码文件。条件编译对于程序的移植和调试很方便。条件编译有三种形式:(1)第一种形式 #ifdef 标识符 程序段1 #else 程序段2 #endifDATE: 2022/7/17PAGE: 82 七、Cx51 预处理-条件编译 如果标识符已被 #define命令定义过则对程序段1进行编译;否则对程序段2进行编译。如果没有程序段2,则可以写为: #ifdef 标识符 程序段 #endifDATE: 2022/7/17PAGE: 83 七、Cx51 预处理-条件编译第二种形式 #ifndef 标识符 程序段1 #else 程序段2 #endif 与第一种形式的区别是将“ifdef”改为“ifndef”。它的功能是,如果标识符未被#define定义过则对程序段1进行编译,否则对程序段2进行编译。这与第一种形式的功能正相反。DATE: 2022/7/
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 2025至2030年中国油脂防哈变酸变剂数据监测研究报告
- 2025至2030年中国幻影面地板数据监测研究报告
- 2025至2030年中国仪表电器数据监测研究报告
- 2025年中国汽车结构钢市场调查研究报告
- 环境金属暴露对糖尿病发病风险的交互作用和混合效应研究
- 2025年度车辆运输合同环保责任履行协议4篇
- 2025年度在线教育平台运营服务合同范本
- 二零二五年度模具生产设备租赁合同3篇
- 2025年度个人消费分期借款合同参考样本2篇
- 2025年度公共文化设施承建与艺术装修合同4篇
- 2024版塑料购销合同范本买卖
- 2024-2025学年人教新版高二(上)英语寒假作业(五)
- JJF 2184-2025电子计价秤型式评价大纲(试行)
- GB/T 44890-2024行政许可工作规范
- 2024年安徽省中考数学试卷含答案
- 2025届山东省德州市物理高三第一学期期末调研模拟试题含解析
- 2024年沪教版一年级上学期语文期末复习习题
- 两人退股协议书范文合伙人签字
- 2024版【人教精通版】小学英语六年级下册全册教案
- 汽车喷漆劳务外包合同范本
- 微项目 探讨如何利用工业废气中的二氧化碳合成甲醇-2025年高考化学选择性必修第一册(鲁科版)
评论
0/150
提交评论