51单片机4位数乘法C语言,51单片机实现4位数以内的加减法

中南民族大学,电子信息工程学院,开设了一门课程,叫《嵌入式电路设计》,由舒老师带头,旨在引导低年级的学生入门嵌入式,其内容比较多,包括模电、数电、C语言、单片机、EDA技术等。最近有位师弟找到我,希望我能帮他指导一下,利用AT89C52单片机设计一个最小系统,其中包括矩阵键盘、数码管显示、中断、2位数加减法、定时计数与暂停等功能。我也粗略的设计了一个,在此分享出来,希望能对初学者有所帮助,使更多的人加入到嵌入式的行业来。

开发工具:keil

仿真工具:proteus

代码如下:

头文件:inc_all.h

1 #ifndef INC_ALL_H_

2 #define INC_ALL_H_

3

4 volatile unsigned char keyValue;

5 volatile unsigned char sign;

6 volatile long int opr1;

7 volatile long int opr2;

8 volatile long int SysValue=0;

9 volatile int keyCounter;

10 volatile int cnt50ms=0;

11 volatile bit StartFlag;

12

13 void Init_Timer0();

14 void Init_Timer1();

15 void delayms(int t);

16 unsigned char KeyScan(void);

17 void showNumber(long int num);

18 void keyAnalyzing(unsigned char keyval);

19

20 #endif

源文件如下:main.c

1 #include

2 #include "inc_all.h"

3 //=======================================================

4 //  数码管显示译码,共阴极

5 //  0,1,2,3,4,5,6,7,8,9,灭,‘E’,'-'

6 //=======================================================

7 unsigned char code table[]={0x3F,0x06,0x5b,0x4F,0x66,

8                             0x6d,0x7d,0x07,0x7F,0x6F,

9                             0x00/* trun off */,

10                             0x79/* Error */,

11                             0x40/* - */};

12 //========================================================

13 //  定时器0初始化函数,定时50毫秒

14 //  用键盘上的“START”键启动计数

15 //  用键盘上的“SUS”键暂停计数

16 //========================================================

17 void Init_Timer0()

18 {

19     TMOD |= 0x01;

20     TH0  = 0x3C;

21     TL0  = 0xB0;

22     TR0  = 0;

23     ET0  = 1;

24 }

25 //=========================================================

26 //  定时器1初始化函数

27 //  定时23毫秒,用于显示

28 //  初始化后计时启动

29 //=========================================================

30 void Init_Timer1()

31 {

32     TMOD |= 0x10;

33     TH1  = 0xA6;

34     TL1  = 0x28;

35     TR1  = 1;

36     ET1  = 1;

37 }

38 //=========================================================

39 //  延时函数

40 //=========================================================

41 void delayms(int t)

42 {

43     int i,j;

44     for(i=t;i>0;i--)

45         for(j=25;j>0;j--)

46             ;

47 }

48 //=========================================================

49 //  四位数码管显示函数

50 //  能自动灭零,自动识别正负号

51 //  数值超出显示范围时显示错误"E---"

52 //=========================================================

53 void showNumber(long int num)

54 {

55     unsigned char q,s,b,g;

56     if(num>=0)

57     {

58         q = num/1000;

59         b = num/100%10;

60         s = num/10%10;

61         g = num%10;

62         if(num<10)

63         {

64             q = 10;

65             b = 10;

66             s = 10;

67         }

68         else if(num<100)

69         {

70             q = 10;

71             b = 10;

72         }

73         else if(num<1000)

74             q = 10;

75         else if(num>9999)

76         {

77             q = 11;     //show error

78             b = 12;

79             s = 12;

80             g = 12;

81         }

82     }

83     else

84     {

85         if(num>-1000)

86         {

87             q = 12;

88             b = (0-num)/100;

89             s = (0-num)/10%10;

90             g = (0-num)%10;

91         }

92         else

93         {

94             q = 11;     //show error

95             b = 12;

96             s = 12;

97             g = 12;

98         }

99     }

100     P0 = 0x00;

101     P0 = table[q];

102     P2 = 0xFE;

103     delayms(10);

104     P0 = 0x00;

105     P0 = table[b];

106     P2 = 0xFD;

107     delayms(10);

108     P0 = 0x00;

109     P0 = table[s];

110     P2 = 0xFB;

111     delayms(10);

112     P0 = 0x00;

113     P0 = table[g];

114     P2 = 0xF7;

115     delayms(10);

116 }

117 //=========================================================

118 //  键盘扫描函数

119 //  返回按键情况,扫描结果

120 //=========================================================

121 unsigned char KeyScan(void)

122 {

123     unsigned char temp=0xF0;

124     P1 = temp;

125     temp = P1;

126     if(temp!=0xF0)

127     {

128         delayms(5);     //去抖动

129         temp = P1;

130         if(temp!=0xF0)

131         {

132             int t=0x01,i;

133             for(i=0;i<4;i++)

134             {

135                 P1 = ~(t<

136                 temp = P1;

137                 switch(temp)                //按行扫描

138                 {

139                     case 0xee:  return '1';

140                     case 0xde:  return '2';

141                     case 0xbe:  return '3';

142                     case 0x7e:  return '+'; //加号

143

144                     case 0xed:  return '4';

145                     case 0xdd:  return '5';

146                     case 0xbd:  return '6';

147                     case 0x7d:  return '-'; //减号

148

149                     case 0xeb:  return '7';

150                     case 0xdb:  return '8';

151                     case 0xbb:  return '9';

152                     case 0x7b:  return 'r'; //复位

153

154                     case 0xe7:  return '0';

155                     case 0xd7:  return 's'; //启动

156                     case 0xb7:  return 't'; //暂停

157                     case 0x77:  return '='; //等于

158                     default:    ;

159                 }

160             }

161         }

162     }

163     return '0';

164 }

165 //=========================================================

166 //  键盘解析函数

167 //  对扫描得到的键值进行解析

168 //=========================================================

169 void keyAnalyzing(unsigned char keyval)

170 {

171     if(keyval>='0' && keyval<='9')

172     {

173         switch(keyCounter)

174         {

175             case 0: SysValue = (int)keyval-0x30;

176                     keyCounter++;

177                     break;

178             case 1: ;

179             case 2: ;

180             case 3: SysValue =SysValue*10+(int)keyval-0x30;

181                     keyCounter++;

182                     break;

183             case 4: SysValue =SysValue*10+(int)keyval-0x30;

184                     keyCounter=0;

185                     break;

186         }

187     }

188     else

189     {

190         switch(keyval)

191         {

192             case '+':   sign = '+';

193                         opr1 = SysValue;

194                         SysValue = 0;

195                         keyCounter = 0;

196                         break;

197             case '-':   opr1 = SysValue;

198                         SysValue = 0;

199                         keyCounter = 0;

200                         sign = '-';

201                         break;

202             case 's':   sign = 's';

203                         TR0 = 1;     //启动计数

204                         StartFlag = 1;

205                         break;

206             case 't':   sign = 't';

207                         if(StartFlag)

208                             TR0 ^= 1;//暂停/启动计数

209                         break;

210             case 'r':   sign = 'r';

211                         opr1 = 0;

212                         opr2 = 0;

213                         SysValue = 0;

214                         keyCounter = 0;

215                         TR0 = 0;    //停止计数器

216                         StartFlag = 0;

217                         break;

218             case '=':   opr2 = SysValue;

219                         if(sign=='+')

220                             SysValue = opr1+opr2;

221                         else if(sign=='-')

222                             SysValue = opr1 - opr2;

223                         opr1 = 0;

224                         opr2 = 0;

225                         keyCounter = 0;

226                         sign = '=';

227                         break;

228         }

229     }

230 }

231 //=========================================================

232 //  主函数main

233 //  全局采用中断方式,有利于降低功耗

234 //=========================================================

235 void main()

236 {

237     EX0 = 1;        //允许外部0中断

238     IT0 = 1;        //外部0中断方式为 “下降沿”

239     Init_Timer0();  /*初始化定时器0,在键盘上点击“START”后

240                     开始计数,定时时间为1秒*/

241     Init_Timer1();  /*初始化定时器1,用于定时显示,定时时间

242                     为23毫秒,即每隔23毫秒调用一次显示函数*/

243     EA  = 1;        //总中断开

244     P1 = 0xF0;      //初始键盘接口

245     while(1) ;

246 }

247 //=========================================================

248 //  按键中断服务函数,采用外部中断0

249 //  按键中断,在中断里面检测按键并解析按键

250 //=========================================================

251 void key_isr(void) interrupt 0

252 {

253     EA = 0;

254     keyValue = KeyScan();

255     keyAnalyzing(keyValue);

256     P1 = 0xF0;

257     EA = 1;

258 }

259 //=========================================================

260 //  定时器0中断服务函数

261 //  用于,定时1秒计数,计数到8888后返回重新新计数

262 //=========================================================

263 void timer0_isr(void) interrupt 1

264 {

265     TR0  = 0;

266     TH0  = 0x3C;

267     TL0  = 0xB0;

268     TR0  = 1;

269     cnt50ms++;

270     if(cnt50ms==19)     //计数20次  20*50 = 1000毫秒,即1秒

271     {

272         cnt50ms = 0;

273         SysValue=(SysValue>8887)?0:SysValue+1;

274     }

275 }

276 //=========================================================

277 //  定时器1中断服务函数

278 //  方式1,定时时间为23毫秒

279 //  用于数码管显示

280 //=========================================================

281 void timer1_isr(void) interrupt 3

282 {

283     TR1  = 0;

284     TH1  = 0xA6;

285     TL1  = 0x28;

286     showNumber(SysValue);

287     TR1  = 1;

288 }

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值