《双积分数字直流电压表.docx》由会员分享,可在线阅读,更多相关《双积分数字直流电压表.docx(12页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。
1、积分式直流数字电压表摘要本双积分电压表系统以89C51单片机为核心、以分立元件制作的双积分型A/D转换器为主要部件的4位半积分式数字直流电压表,并对所设计的电压表进行了测试,结果测量误差0.03%,精度达到4位半。实现了自动量程转换功能,自动调零功能,有很好的实际应用价值。 关键词:单片机,双积分A/D转换器,自动调零,自动转换量程目录1 方案论证与比较11.1信号调理11.2 处理器的选择与比较11.3 积分器的选择与比较12 系统设计22.1 总体设计22.2 单元电路设计32.2.1 信号调理调理电路 32.2.2 双积分电路设计42.2.3 基准源电路设计43 软件设计54系统测试55
2、 结论6参考文献:6附录:7附1:元器件明细表:8附2:仪器设备清单8附3:电路图图纸9附4:程序清单 方案论证与比较1.1.1 信号调理比较与选择方案一、信号经过缓冲器提高输入阻抗后经过低通滤波器后,然后由模拟开关选择信号放大与不放大,当信号大于200mv时不放大,小于200mv时经过仪表放大器进行放大。方案二、信号经过电压分阻条统一衰减后经过缓冲器提高其负载能力,信号进行低通滤波器其截止频率在10HZ左后滤除高频噪声及干扰,然后经过低噪声,高精度运放放大。方案论证:方案一对不同信号进行放大其电路复杂,当测量多个量程时放大电路的增益不一样,需多个放大电路成本很高,且用仪表放大器价格过于昂贵。
3、方案二通过统一衰减后在进行放大其电路简单调试方便。所以采用方案二。 1.2 处理器的比较与选择STC单片机所特有的在线下载功能和其他公司的单片机不同,不是利用SPI进行在线编程,而是利用IAP功能,在系统运行时编程,因此,可以通过串口来对单片机进行编程。其电路极为简单,只要所使用的单片机系统具有232串口通信功能即可。.工作宽温度范围,-4085,在系统可编程,无需编程器,可远程升级,抗干扰强.价格低廉,所以采用了STC单片机.1.3积分器比较与选择方案一、采用双极性运放UA741,UA741为通用运放价格便宜,容易购买。积分电容选择胆电容进行积分。方案二、采用FET运放TL062,其漏电流小
4、,电容选择独石电容。方案论证:方案一ua741器基集电流大,失调电流大对积分产生影响,且胆电容的漏电流大也对积分产生一定影响,而方案二TL062为FET型输入阻抗高基集电流小且独石电容漏电流小。所以才用方案二。2 系统设计2.1 总体设计本设计基于STC89C51单片机的4位半积分式直流数字电压表设计的设计思路及实现方法。在设计中,充分利用了89C51单片机内部的高速计数器和以分立元件组成的双积分型A/D转换器的优良特性,使整个设计达到了比较满意的效果。硬件设计主要有双电源电路、信号采集电路、量程转换电路、开关逻辑控制电路、积分比较与自动回零电路、单片机系统、显示电路组成。软件编程采用模块化结
5、构,主要有时序子程序,系数运算子程序, BCD码转换子程序,自动量程转换子程序,显示子程序等组成。信号经过电阻分压器统一衰减后,经过运放缓冲后在经过高精度,低噪声,失调电压小的运放OP37放大,开始先对信号进行积分,后开始对基准源进行反积分,然后经过单片机运算处理后有单片机显示。 图一2.2 单元电路设计 2.2.1 信号调理调理电路 图二信号经过电压分阻条统一衰减后经过缓冲器提高其负载能力,信号进行低通滤波器其截止频率在10HZ左后滤除高频噪声及干扰,然后经过低噪声,高精度运放放大。放大倍数可有可变电阻进行调整补偿。2.2.2 双积分电路设计 图三单片机通过对开关逻辑控制电路来控制双积分A/
6、D转换,单片机先控制开关逻辑控制电路使s2接通进行自动回零,接着OUT2接通将待测电压进行正积分,再使Vref接通对反积分基准电压进行反积分,同时单片机内部计数器开始计数,到一定时间后比较电路中的比较电路输出中断信号,单片机停止计数并将计数值滤波,通过减法、乘法和除法的系数运算最后转换成BCD码,再通过显示电路将待测电压值显示出来。A/D转换是在单片机和开关逻辑控制电路的控制下有条不紊地进行,全部过程可分三个阶段:(1)正积分:也称信号采集阶段。在这个阶段,通过单片机对开关逻辑控制电路的控制对检测电压out2积分。积分器的输出电压随时间线性地增加。正积分时间由单片机控制,定时为T1,在T1结束
7、时积分器的输出电压为: Vout(T1)=-1C2*R9out2 (公式一)(2)反积分:也称计数阶段。在这个阶段,通过单片机对开关逻辑控制电路的控制对基准电压ref积分。经过T2时间后回到0, Vout2(T2)=Vout1+1C2*R9Vref (公式二) T2=out2*T1/T2 (公式三)由此可以看出T2的大小取决于输入待测电压Vx的大小。(3)自动回零:也称复位阶段,在该阶段,因反积分使比较器输出由高电平变成低电平,再由单片机控制开关逻辑控制电路动作,使VA导通,使得积分电容充分放大。2.2.3 基准电压电路设计 图四负电源电压采用高精度可编程稳压器件TL431产生,然后进过电源滤
8、波。在经过缓冲器进行隔离,以免后级电路对基准源产生负载影响,影响基准源的精度。3 软件设计控制芯片为STC89C52,由于处理器速度较快,所以采用c语言编程方便简单.软件流程如图下 电压表主流程图4系统测试 电压测试数据(室温条件下)标准电压值自动量程选择实测电压值误差/1.000mV200mV档01.00mV050.000mV 200mV档50.00mV0120.000mV档200mV120.01mV0.008199.990mV档200mV199.97mV-0.010.20020V2V档0.2000V-0.011.25000V2V档1.2503V0.0241.98000V2V档1.9804V
9、0.020从标准稳压电源输出标准的待测电压,用5位半数字电压表作为校准设备,分别用5位半数字电压表和本电压表对待测电压进行测试,并对测试结果进行了比较,如表1所示。测试结果表明,本电压表的测量误差0.03%,精度达到4位半。当测量199.990mV和0.20020V两组标准电压值时,本电压表进行了自动量程转换,由此表明本电压表具有200mV和2V两个量程并且可以实现自动量程转换功能。5 结论由于系统架构设计合理,功能电路实现较好,系统性能优良、稳定,较好地达到了题目要求的各项指标。参考文献:1模拟电子线路基础,吴运昌著,广州:华南理工大学出版社,2004年;2数字电子技术基础,阎石著,北京:高
10、等教育出版社,1997年;3单片机原理及应用,李建忠著,西安:西安电子科技大学,2002年;4王剑铭,黄俊杰,宁彦卿.新颖实用的单片机双积分A/D转换电路和软件J.郑州工业大学学报,2001;5李伟.一种高精度低成本A/D转换器的原理和实现J.自动化仪表,2007;6冯文涛,于明鑫.单片机控制的高精度双积分ADCJ.辽宁师专学报,2004;附录:附1:元器件明细表:1、STC89C522、TL0623、OP374、1602液晶附2:仪器设备清单1、 低频信号发生器 2、 数字万用表 3、 数字示波器4、 稳压电源附3:电路图图纸 整体电路图附4:程序清单/SW1 S1 S0 00 A4 Vin
11、 11 A7 GND /SW2 S1 S0 10 A6 Vref 11 A7 GND 01 A5 Vin/SW3 S 0 导通 1 断开/#include #include #define uchar unsigned char #define uint unsigned int #define LCD_DATA P0 sbit LCD_RS = P24; sbit LCD_RW = P25; sbit LCD_EN = P26; sbit change_in = P30;sbit S2 = P31;sbit S3 = P32;sbit S4 = P34;sbit S5 = P35;/sbit
12、 S6 = P36;sbit P1_7 = P17; sbit cmp_in = P33; sbit P1_4 = P10; sbit P1_5 = P11;sbit P1_6 = P12; uchar compares_zero = a ,first_integral = b,second_integral = c, discharge = d, Operation = e;/状态定义为 校零 第一次积分 第二次积分 电容放电 运算 uchar state;uint regser; uchar code dis1 = current voltage; uchar dis2 = 00000 m
13、v ; uchar cnt=0; /* 延时子程序 void delay(uint ms) uchar i; while(ms-) for(i = 0; i 250; i+) _nop_(); _nop_(); _nop_(); _nop_(); /*检查LCD忙状态 /*lcd_busy为1时,忙,等待。lcd-busy为0时,闲,可写指令与数据。 bit lcd_busy() bit result; LCD_RS = 0; LCD_RW = 1; LCD_EN = 1; _nop_(); _nop_(); _nop_(); _nop_(); result = (bit)(LCD_DATA&
14、0x80); LCD_EN = 0; return result; /*写指令数据到LCD /*RS=L,RW=L,E=高脉冲,D0-D7=指令码。 void lcd_wcmd(uchar cmd) while(lcd_busy(); LCD_RS = 0; LCD_RW = 0; LCD_EN = 1; LCD_DATA = cmd; _nop_(); _nop_(); _nop_(); _nop_(); LCD_EN = 0; /*写显示数据到LCD /*RS=H,RW=L,E=高脉冲,D0-D7=数据。 void lcd_wdat(uchar dat) while(lcd_busy();
15、 LCD_RS = 1; LCD_RW = 0; LCD_EN = 1; LCD_DATA = dat; _nop_(); _nop_(); _nop_(); _nop_(); LCD_EN = 0; /* 设定显示位置 void lcd_pos(uchar pos) lcd_wcmd(pos|0x80); /数据指针=80+地址变量 /* LCD初始化设定 void lcd_init() delay(15); /等待LCD电源稳定 lcd_wcmd(0x38); /16*2显示,5*7点阵,8位数据 delay(5); lcd_wcmd(0x0c); /显示开,关光标 delay(5); l
16、cd_wcmd(0x06); /字符进入 delay(5); lcd_wcmd(0x01); /清除LCD的显示内容 delay(5); /* 清屏子程序 void lcd_clr() lcd_wcmd(0x01); /清除LCD的显示内容 delay(5); /显示函数void display_line( uchar *p,uchar line) if(line = 1) lcd_pos(0x00); else if(line =2) lcd_pos(0x40); while(*p) lcd_wdat(*p); p+;/SW1 S1 S0 00 A4 Vin 11 A7 GND /SW2 S
17、1 S0 10 A6 Vref 11 A7 GND 01 A5 Vin/SW3 S 1 导通 0 断开 void compare ( ) P1_4=1; P1_5=0; P1_6=0; if(cmp_in = 1)/ state = first_integral; else/ S1 = 0; /校零时接地 if(change_in = 0) S2 = 0; /接入放大器 else S2 = 1; S3 = 1; /将积分输入端接非参考电压 S4 = 1; /对调零电容充电 S5 = 1; /积分电容非放电 /S6 = 1; /参考电压电容充电 /delay(100); void f_integ
18、ral () P1_4=0; P1_5=1; P1_6=0; if(change_in = 0) S2 = 0; /接入放大器 else S2 = 1; S3 = 1; /将积分输入端接非参考电压 S4 = 0; /对调零电容断开 S5 = 0; /积分电容非放电 /S6 = 1; /参考电压电容充电 TMOD |=0x10; TH1 =0x15; TL1 =0xa0; ET1=1; TR1=1; EA=1 void s_integral() if(change_in = 0) S2 = 0; else S2 = 1; S3 = 0; /将积分输入端接参考电压 S4 = 1; /对调零电容断开
19、 S5 = 0; /积分电容非放电 P1_4=1; P1_5=1; P1_6=0; TMOD |=0x90; TH1 =0x00; TL1 =0x00; ET1=1; TR1=1; EA=1; /S6 = 0; while( state =second_integral ) if(cmp_in = 0) regser = 0x00ff&TH1; regser=8; regser = regser+TH0; state = Operation;void Operation_display () uchar a,b,c,d,e; uchar vref = 20; float result; uin
20、t midle ; P1_4=0;P1_5=0; P1_6=1; if(change_in = 0)S2 = 0; /接入放大器 else S2 = 1;S3 = 1; /将积分输入端接非参考电压S4 = 1; /对调零电容充电S5 = 1; /积分电容非放电/S6 = 1; /参考电压电容充电 result = (float)regser)/6)*vref); if(change_in = 0) result =result/9.2625; midle = (uint)result; a = (uint)result/10000; midle = midle%10000; b = midle
21、/1000; midle = midle%1000; c= midle/100; midle = midle%100; d= midle/10; e = midle%10; dis21 = a + 0x30; dis22 = b + 0x30; dis23 = c + 0x30; dis25 = d + 0x30; dis24 = .; dis26 = e + 0x30; dis27 = m; dis28 = V; dis29 = ; else result =result/9.2500;/10.0019; midle = (uint)result; a = (uint)result/1000
22、0; midle = midle%10000; b = midle/1000; midle = midle%1000; c= midle/100; midle = midle%100; d= midle/10; / midle = midle%10; e = midle%10; if(result =20000) dis21 = a + 0x30; dis22 = .; dis23 = b + 0x30; dis24 = c + 0x30; dis25 = d + 0x30; /dis24 = .; dis26 = e + 0x30; dis27 = ; dis28 = V; dis29 =
23、; else dis21 = o; dis22 = v; dis23 = e; dis24 = r; dis25 = ; dis26 = ; dis27 = ; dis28 = ; dis29 = ; if(cnt = 4) cnt=0; display_line(dis2,2); else cnt+; state = compares_zero;/* 中断函数 void T1_interrupt() interrupt 3 using 1 P1_7 = P1_7 ; if(cmp_in = 0) state = Operation; else state = second_integral;
24、 TR1=0;/* 主程序 main() P1=0xff;state = compares_zero;cmp_in = 1; delay(10); lcd_init(); lcd_clr(); display_line(dis1,1); display_line(dis2,2); while(1) if(state = compares_zero) compare (); else if(state = first_integral) f_integral (); while(state = first_integral); else if(state = second_integral) s_integral(); /else if(state = discharge) /uncharge (); else if(state = Operation) Operation_display ();