ImageVerifierCode 换一换
格式:DOCX , 页数:20 ,大小:19.20KB ,
资源ID:3309579      下载积分:12 金币
快捷下载
登录下载
邮箱/手机:
温馨提示:
快捷下载时,用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)。 如填写123,账号就是123,密码也是123。
特别说明:
请自助下载,系统不会自动发送文件的哦; 如果您已付费,想二次下载,请登录后访问:我的下载记录
支付方式: 支付宝    微信支付   
验证码:   换一换

加入VIP,免费下载
 

温馨提示:由于个人手机设置不同,如果发现不能下载,请复制以下地址【https://www.bdocx.com/down/3309579.html】到电脑端继续下载(重复下载不扣费)。

已注册用户请登录:
账号:
密码:
验证码:   换一换
  忘记密码?
三方登录: 微信登录   QQ登录  

下载须知

1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。
2: 试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
3: 文件的所有权益归上传用户所有。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 本站仅提供交流平台,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

版权提示 | 免责声明

本文(基于Atmega16的温度测控系统PID算法.docx)为本站会员(b****6)主动上传,冰豆网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知冰豆网(发送邮件至service@bdocx.com或直接QQ联系客服),我们立即给予删除!

基于Atmega16的温度测控系统PID算法.docx

1、基于Atmega16的温度测控系统PID算法/编译器:AVRStudio头文件部分:#include #define uchar unsigned char#define uchar unsigned char #define uint unsigned intvoid convert(float data); void init_1820(void); void write_1820(uchar x); uchar read_1820(void);float read_temperature(void);char key_scan();int lcd_bz();void lcd_wcmd(u

2、char cmd);void lcd_pos(uchar pos);void lcd_wdat(uchar dat); void lcd_wstr(unsigned char pos,unsigned char *q);void lcd_init();void avr_init();void delay(int us);void delayl(int ms);void delay1(int ms);按键程序#include#includeheadfile.h/.按键.char key_scan() int temp=0,temp1,temp2; char key; DDRA=0xf0; POR

3、TA&=0x0f; delay1(3); temp1=PINA&0x0f; if(temp1!=0x0f) delay1(80); temp1=PINA&0x0f; if(temp1!=0x0f) DDRA=0x0f; PORTA&=0xf0; delay1(5); temp2=PINA&0xf0; if(temp2!=0xf0) temp=temp1+temp2; switch(temp) case 0xee:key=/;break;/7 case 0xde:key=*;break;/8 case 0xbe:key=-;break;/9 case 0x7e:key=+;break;/+ ca

4、se 0xed:key=.;break;/4 case 0xdd:key=9;break;/5 case 0xbd:key=6;break;/6 case 0x7d:key=3;break;/- case 0xeb:key=;break;/1 case 0xdb:key=8;break;/2 case 0xbb:key=5;break;/3 case 0x7b:key=2;break;/* case 0xe7:key=0;break;/0 case 0xd7:key=7;break;/. case 0xb7:key=4;break;/= case 0x77:key=1;break;/ defa

5、ult :key=0;break; return key;1602显示程序#include /#include#define ep_1 (PORTB|=0x04)#define ep_0 (PORTB&=0x04)#define rs_1 (PORTB|=0x01)#define rs_0 (PORTB&=0x01)#define rw_1 (PORTB|=0x02)#define rw_0 (PORTB&=0x02)#define uchar unsigned char #define uint unsigned int/.LCD./. 测试LCD忙碌状态.int lcd_bz() DDRC

6、&=0x80; int result=0; rs_0; rw_1; ep_1; result =(result|(PINC & 0x80); ep_0; DDRC=0xff; return result; /. 写入指令数据到LCD.void lcd_wcmd(uchar cmd) while(lcd_bz(); rs_0; rw_0; ep_0; PORTC= cmd; ep_1; ep_0; delay(5);/.设定显示位置.void lcd_pos(uchar pos) lcd_wcmd(pos | 0x80);delay(5);/.写入字符显示数据到LCD.void lcd_wdat

7、(uchar dat) while(lcd_bz(); rs_1; rw_0; ep_0; PORTC=dat; ep_1; ep_0; /.写入字符显示数组到LCD.void lcd_wstr(unsigned char pos,unsigned char *q) /lcd_wcmd(0x01); /清屏 /delay(10); unsigned char i=0x00; lcd_pos(pos); while(*q!=0) lcd_wdat(*q); q+; i+; if(i=(0x0F-pos+1) lcd_pos(0x40); delay(10); /*/.LCD初始化设定.void

8、lcd_init() lcd_wcmd(0x38); /function set delay(10); lcd_wcmd(0x38); /function set delay(10); lcd_wcmd(0x0c); /display on/off delay(10); lcd_wcmd(0x06); /entry mode set delay(10); lcd_wcmd(0x01); /清除LCD的显示内容 delay(10);/.avr初始化./void avr_init() DDRC=0xFF; DDRB=0x07; 18b20程序#include #define uchar unsig

9、ned char#define uchar unsigned char #define uint unsigned int/-/.convert:data display.void convert(float data) /实数在液晶上显示 int i=0; int data1=(int)data; uchar array15=0,array25=0; lcd_wcmd(0x01); / lcd_wcmd(0x00); lcd_pos(0x0B); / if(data1=0) array10=0; lcd_wdat(48); / delay1(5); else while(data1!=0)

10、array1i=data1%10; data1=data1/10; i+; for(-i;i=0;i-) lcd_wdat(array1i+48); / delay1(5); /显示小数点前面 lcd_wdat(0x2E); /显示小数点 for(i=0;i2;i+) /显示小数部分前两位 data=data*10; array2i=(int)data)%10; lcd_wdat(array2i+48); /delay1(5); /.18B20.void init_1820(void) int Flag_1820Error; uchar i; uint j=0; PORTD|=(17);/PO

11、RTC|=(17); /1 PORTD&=(17);/PORTC&=(17); /0 for(i=0;i8;i+)delay(180);/delay_60us();/480us以上 PORTD|=(17);/PORTC|=(17); /1 DDRD&=(17);/DDRC&=(17); /PINC7 is INPUT delay(40);/delay_15us(); /1560us delay(40);/delay_15us(); Flag_1820Error=0; while(PIND&(17)/while(PINC&(1=18000)Flag_1820Error=1;break; DDRD

12、|=(17);/DDRC|=(17); /PORTC7 is OUTPUT PORTD|=(17);/PORTC|=(17); /1 for(i=0;i4;i+)delay(180);/delay_60us(); /240us /*/*/void write_1820(uchar x) uchar m; for(m=0;m8;m+) if(x&(1m) /写数据,从低位开始 PORTD&=(17);/PORTC&=(17);delay_5us(); /0,5us PORTD|=(17);/PORTC|=(17); /write1 delay(40);/delay_15us(); /1545us

13、 delay(40);/delay_15us(); delay(40);/delay_15us(); else PORTD&=(17);/PORTC&=(17);delay_15us();/0,15us delay(40);/delay_15us(); /write0 delay(40); /delay_15us(); /1545us delay(40);/delay_15us(); PORTD|=(17);/PORTC|=(17); /1 PORTD|=(17);/ PORTC|=(17); /1 /*/uchar read_1820(void) uchar temp,k,n; temp=0

14、; for(n=0;n8;n+) PORTD&=(17);/PORTC&=(17); /0 delay(13);/delay_5us(); PORTD|=(17);/PORTC|=(17); /1 delay(13);/delay_5us(); DDRD&=(17);/DDRC&=(17); /PINC7 is INPUT k=(PIND&(17);/k=(PINC&(17); /读数据,从低位开始 if(k) temp|=(1n); /read1 else temp&=(1n); /read0 delay(40);/delay_15us(); /45us delay(40);/delay_1

15、5us(); delay(40);/delay_15us(); DDRD|=(17);/DDRC|=(17); /PORTC7 is OUTPUT return (temp); /*/float read_temperature(void) float temp;/ uchar teml=0,temh=0; unsigned long t=0; init_1820(); /复位18b20 write_1820(0xcc); / 发出转换命令 write_1820(0x44); /Delay_nms(100); init_1820(); write_1820(0xcc); /发出读命令 writ

16、e_1820(0xbe); teml=read_1820(); /读数据byte1 temh=read_1820(); /byte2 t=temh; t=t8; t=t|teml; temp=t*0.0625*260/286; return(temp); /*if(temh&0xf8)sign=0; else sign=1; if(sign=0)temh=255-temh;teml=255-teml; temh=temh4; teml=teml&0x0f; teml=(teml*10)/16; tempval=temh;e0=tempval/100; tempval=temh;e1=(temp

17、val/10)%10; tempval=temh;e2=tempval%10; tempval=teml;e3=tempval;*/ Main程序 #include#includeheadfile.h#include#include#include#include#includeunsigned char key5; /按键数组float keyvalue; /按键值float actual; /温度值unsigned int flag=0;/判断按键标志unsigned char dis1=SET;unsigned char dis2=NOW;unsigned char dis3=00:00

18、;unsigned int h=0; /定时1S计时10000次unsigned count=0; /计算动态时间float PWM=0;float PWM1=0;float Error1; /误差unsigned int maxminflag=0;/判断达到动态平衡标志unsigned char time7;/存储动态时间struct PIDfloat SetPoint; / 设定目标 Desired Valuefloat Proportion; / 比例常数 Proportional Constfloat Integral; / 积分常数 Integral Constfloat Deriv

19、ative; / 微分常数 Derivative Constfloat LastError; / Error11float PrevError; / Error12;struct PID spid; / PID Control Structurestruct PID *pp;/*PID 结构体初始化*/void PIDInit (struct PID *pp) memset(pp,0,sizeof(struct PID);/*PID 参数设置*/void setPID(float a,float b,float c)pp-Proportion=a;pp-Integral=b;pp-Deriva

20、tive=c;/*PID 计算部分*/float PIDCalc( struct PID *pp, float NextPoint )float dError;unsigned int a;Error1 = pp-SetPoint-NextPoint; / 当前偏差 if(fabs(Error1)Proportion*(Error1-pp-LastError) +a*pp-Integral*pp-LastError +a*pp-Derivative*(Error1-2*pp-LastError+pp-PrevError);/*dError=pp-Proportion*Error1 -pp-In

21、tegral*pp-LastError +pp-Derivative*pp-PrevError;if(fabs(Error1)Proportion*(Error1-pp-LastError)+a*pp-Integral*pp-LastError+pp-Derivative*(Error1-2*pp-LastError+pp-PrevError);*/pp-PrevError = pp-LastError;pp-LastError = Error1;return (dError); / 微分项/*PWM 占空比设置/*/void setPWM(float dError) if(fabs(Erro

22、r1)10)PWM+=4*dError; else PWM+=6*dError; /PWM+=6*dError; PWM1=1023-PWM; if(PWM11020)PWM1=1020; OCR1BH=(int)(PWM1/256); OCR1BL=(int)PWM1%256;void factor(void) /确认按键值 unsigned char tmp; int i=0; int temp1,temp2; flag=0; float key1=0,key2=0; while(!flag) while(!(tmp=key_scan(); if(tmp=*) flag=1; else if(tmp=)flag=2; else keyi=tmp; lcd_pos(0x03+i); lcd_wdat(keyi); i+; keyi=0; keyvalue=(key0-48)*10+(key1-48)+(key3-48)*0.1+(key4-48)*0.01+0.5;/0.5是矫正 /* for(i=0;i=0&temp1=0;i-) key1=key1+(keyi-48)*pow(10,temp1-1-i);/10(temp1-1-i) for(i=temp1+1;iSetPoint=keyvalue;/*从DS18B20 获得实际温度值并设置显示位置*

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1