简易四则运算计算器(C51单片机实现)

来源:互联网 发布:java加密算法有哪些 编辑:程序博客网 时间:2024/05/17 02:39

【说明】

    这是嵌入式课程的一个小作业,用C51单片机,实现了0-255内的简易四则运算,暂不支持负数、溢出等特殊情况的处理。


【关键点】

    1、计算器用R5、R6、R7三位显示,段码为0,全暗,段码为0xff,全亮。

    2、R3用于保存运算符

    3、两数都用B压入栈中,最后取结果时可以分别弹出,并根据操作符计算。

    4、程序在两数的第一位默认都输入数字,其他位置皆可复位。

    5、一次计算完成后、按任意键复位。


【键盘位置】



代码:

;3位0-255计算器,支持四则运算;按键有0-9、+、-、*、/、复位、=;R5,R6,R7分别用于显示三位;暂不支持负数、溢出处理ORG0000HLJMPSTARTWCEQU P0 ;数码管位控DCEQU P1  ;数码管段控KCEQU P2  ;键盘检测ORG0030HSTART:     MOV R5,#0 MOV R6,#0 MOV R7,#0N1_B1: ACALLKEYDOWN CJNER4,#0x10,PRO1;检测到按键做相应处理  ACALLDISPLAY JMPN1_B1;否则继续检测PRO1: MOVA,R4 MOVR0,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR5,AN1_B2: ACALLDISPLAY ACALLKEYDOWN CJNE   R4,#0x10,PRO2 ;检测按键,有键按下做相应处理 JMPN1_B2PRO2: MOVA,R4 ACALLJUDGE_OPER ;检查是否为操作符 CJNER3,#0x04,CON1 ;是清除键,直接复位 JMPSTARTCON1: CJNER3,#0x06,PRO3 ;是操作符,跳转到PRO3          MOVA,R4 ;是数字 MOVR1,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR6,A MOVR4,#0x10 JMPN1_B3PRO3:     MOVB,R0 ;将num1的结果保存在B中 PUSHB JMPN2_B1 ;转去判断第2个数的第1位N1_B3: ACALLDISPLAY ;第1个数字第3位 ACALLKEYDOWN CJNE   R4,#0x10,PRO4 ;检测按键,有键按下做相应处理 JMPN1_B3PRO4:     MOVA,R4 ACALLJUDGE_OPER ;检查是否为操作符 MOVA,R3 CJNEA,#0x04,CON2 ;是清除键,直接复位 JMPSTARTCON2:  CJNEA,#0x06,PRO5 ;等于则是数字,不等于则是操作符 MOVA,R4 ;是数字 MOVR2,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR7,A MOVA,R0 ;保留第1位数 MOVB,#100D MULAB MOVR0,A ;将百位保留在R0 MOVA,R1 ;保留第2位数 MOVB,#10D MULAB MOVR1,A ;将十位保留在R1 MOVA,R2 ;相加 ADDA,R1 ADDA,R0 MOVB,A ;将第1位数先存在B中 PUSHB     JMPOPERPRO5:     MOVA,R0 MOVB,#10D MULAB MOVR0,A  MOVA,R1 ADDA,R0 MOVB,A PUSH       B JMPN2_B1OPER:     ACALLDISPLAY  ACALLKEYDOWN MOVA,   R4 CJNEA,   #0x10,PRO6 ;有键按下 JMPOPERPRO6: MOVA,   R4 ACALLJUDGE_OPER MOVA,   R3 CJNEA,   #0x04,N2_B1 ;不等于是操作符,等于是复位键 JMPSTARTN2_B1: ACALLDISPLAY ;第2个数第1位 ACALLKEYDOWN MOVA,R4 CJNEA,#0x10,PRO7 ;有键按下 JMPN2_B1PRO7: MOVA,R4 ;保留原有操作符 PUSH0x03 ;保存R3中的操作符标记 ACALLJUDGE_OPER MOVA,R3 POP0x03 CJNEA,#0x04,CON3 ;判断是否是复位键 JMPSTARTCON3: MOVA,R4 MOVR0,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR5,A MOVR6,#0x00  ;清除后两位显示 MOVR7,#0X00N2_B2:     ACALLDISPLAY ACALLKEYDOWN MOVA,R4 CJNEA,#0x10,PRO8 ;有键按下 JMPN2_B2PRO8: MOVA,R4 ;保留原有操作符 PUSH0x03 ;保存R3中的操作符标记 ACALLJUDGE_OPER MOVA,R3 POP0x03 CJNEA,#0x04,CON4 ;不是清除键继续判断 JMPSTARTCON4: CJNEA,#0x06,PRO9 ;不相等说明是操作符,相等说明是数字 MOVA,R4 MOVR1,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR6,A JMPN2_B3PRO9: CJNEA,#0x05,MIDNODE ;不是等于号,出错返回 MOVA,R0 MOVB,A PUSHB JMPEDISN2_B3:     ACALLDISPLAY ACALLKEYDOWN MOVA,R4 CJNEA,#0x10,PRO10  JMPN2_B3PRO10: MOVA,R4 ;保留原有操作符 PUSH0x03 ;保存R3中的操作符标记 ACALLJUDGE_OPER MOVA,R3 POP0x03 CJNEA,#0x04,CON5 ;不是清除键继续判断 JMPSTARTCON5:     CJNEA,#0x06,PRO11 ;不相等说明是操作符 MOVA,R4 MOVR2,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR7,A MOVA,R0 MOVB,#100D MULAB MOVR0,A MOVA,R1 MOVB,#10D MULAB MOVR1,A MOVA,R2 ADDA,R1 ADDA,R0 MOVB,A PUSHB JMPAKMIDNODE:     JMPSTARTPRO11: CJNEA,#0x05,MIDNODE   ;通过中继节点返回 MOVB,#10D MOVA,R0 MULAB ADDA,R1 MOVB,A PUSHB JMPEDIS     AK: ACALLDISPLAY ACALLKEYDOWN MOVA,R4 CJNEA,#0x10,EDIS JMPAKEDIS: POP    B MOVA,B POPB MOVR0,A   ;交换AB MOVA,B MOVB,R0 MOVR1,A MOVA,R3 CJNEA,#0x00,   NXT1    ;通过R3的值,判断运算符 MOVA,R1;并进行相应运算 ADDA,B JMPTSNXT1: CJNEA,    #0x01,   NXT2 MOVA,R1 SUBBA,B JMPTSNXT2: CJNEA,#0x02,   NXT3 MOVA,R1 MULAB JMPTSNXT3: CJNEA,   #0x03,     MIDNODE MOVA,   R1 DIVABTS:   ;转换显示     MOVR0,A MOVB,#100D DIVAB MOVR1,A MOVDPTR,#DCODE MOVC A,@A+DPTR MOVR5,A MOVA,B MOVB,#10D DIVAB MOVDPTR,#DCODE MOVCA,@A+DPTR MOVR6,A MOVA,B MOVDPTR,#DCODE MOVCA,@A+DPTR MOVR7,ARESTART:     ACALLDISPLAY ACALLKEYDOWN MOVA,R4 CJNEA,#0x10,MIDNODE JMPRESTART ;按键检测程序,若有键按下,返回0-15,无键按下返回16KEYDOWN:        MOVR4,#0x10MOV KC,#0x0FMOV A,KCCJNE A,#0X0F,PRO ;检测列RETPRO:ACALL DELAY ;延时消抖MOV A,KCCJNE A,#0X0F,COL;确认有键按下RETCOL:COL1:MOV A,KCCJNE A,#0X07,COL2;判断哪一列MOV R4,#0HJMP ROWCOL2:CJNE A,#0X0B,COL3MOV R4,#4HJMP ROWCOL3:CJNE A,#0X0D,COL4MOV R4,#8HJMP ROWCOL4:CJNE A,#0X0E,BACK        ;没有列被按下,直接返回MOV R4,#0CHROW:MOV KC,#0XF0            ;行检测MOV A,KCROW1:CJNE A,#0X70,ROW2MOV A,R4ADD A,#3HMOV R4,AJMP BACKROW2:CJNE A,#0XB0,ROW3MOV A,R4ADD A,#2HMOV R4,AJMP BACKROW3:CJNE A,#0XD0,ROW4MOV A,R4ADD A,#1HMOV R4,AJMP BACKROW4:BACK:MOVA,R4CJNEA,#0x10,DYRETDY:ACALLDELAYACALL DELAYACALLDELAYACALLDELAYRET;数码管显示3位数字,分别存在R5,R6,R7DISPLAY:        PUSH0x00PUSH0x01        MOV R0,#0        ;输出位码MOV DPTR,#WCODEMOV A,R0MOVC A,@A+DPTRMOV WC,A;输出段码MOV     A,R5MOVDC,AMOVR1,#0x0fLP1:        ;延长单位显示时间DJNZ R1,LP1MOVDC,#0INC R0   ;输出位码MOV DPTR,#WCODEMOV A,R0MOVC A,@A+DPTRMOV WC,A;输出段码MOV     A,R6MOVDC,AMOVR1,#0x0fLP2:        ;延长单位显示时间DJNZ R1,LP2MOVDC,#0INC R0        ;输出位码MOV DPTR,#WCODEMOV A,R0MOVC A,@A+DPTRMOV WC,A;输出段码MOV     A,R7MOVDC,AMOVR1,#0x0fLP3:        ;延长单位显示时间DJNZ R1,LP3MOVDC,#0POP0x01POP0x00RET;判断A中是什么操作符,+ — * / reset =分别对应R3中的值为0-5,;若不是操作符,则R3中的值被设置为6JUDGE_OPER: MOVR3,#6AD:     CJNEA,#0x0a,SB ;不是加号,跳到减号 MOVR3,#0 ;0代表加法 RETSB: CJNEA,#0x0b,ML ;不是减号,跳到乘号 MOVR3,#1 ;1代表减法     RETML:     CJNE       A,#0x0c,DV ;不是乘号,跳到除号 MOVR3,#2 ;2代表乘法 RETDV:     CJNEA,#0x0d,CL ;不是除号,跳到清除键 MOVR3,#3 ;3代表除法 RETCL:     CJNEA,#0x0e,EU ;不是清除键,跳到等号 MOVR3,#4 ;4代表清除键 RETEU:     CJNEA,#0x0f,FN ;不是等号,返回 MOVR3,#5 ;5代表等号FN:     RET;延时程序DELAY:        PUSH 0x00;保护现场,R0,R1PUSH 0x01MOV R0,#96H  LP4:MOV R1,#82H  LP5:DJNZ R1,LP5DJNZ R0,LP4POP 0x01;还原现场POP 0x00RET WCODE: DB  0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f   ;位码 DCODE: DB  0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f     ;段码 NUM1:  DB0xff,0xff,0xff;操作数1 NUM2:  DB  0xff,0xff,0xff;操作数2END


0 0
原创粉丝点击