温控炉.docx

上传人:b****6 文档编号:4327346 上传时间:2022-11-29 格式:DOCX 页数:52 大小:294.14KB
下载 相关 举报
温控炉.docx_第1页
第1页 / 共52页
温控炉.docx_第2页
第2页 / 共52页
温控炉.docx_第3页
第3页 / 共52页
温控炉.docx_第4页
第4页 / 共52页
温控炉.docx_第5页
第5页 / 共52页
点击查看更多>>
下载资源
资源描述

温控炉.docx

《温控炉.docx》由会员分享,可在线阅读,更多相关《温控炉.docx(52页珍藏版)》请在冰豆网上搜索。

温控炉.docx

温控炉

杨晓丹曹威 | 自动实1301 | 2015年7月15日

温控炉实验报告

目录

一、实验内容及目的3

二、实验方案内容3

1.温度测量设计3

1)温度测量原理3

2)测温电路设计4

3)温度与电压的对应关系6

2.单片机程序设计7

1)程序功能7

2)PID控制程序7

3)数码管显示8

4)串口通信9

5)上位机控制指令的接收和执行9

6)A/D采样10

7)温度与AD测量值的转换10

8)按键扫描10

9)按键的功能表11

10)PWM方波11

11)多任务处理11

3.上位机程序设计12

1)上位机串口通信12

2)上位机控制12

4.PID算法的设计及其优化12

1)系统辨识12

2)PSO参数优化14

5.温控炉控制实验15

1)单片机控制15

2)上位机控制15

三、实验结果及分析15

1.单片机控制15

2.上位机控制16

四、实验中遇到的问题16

五、附录17

1.上位机主程序17

2.上位机子程序18

3.数据处理程序21

4.系统辨识主程序22

5.系统辨识子程序24

6.PSO参数优化主程序24

7.PSO参数优化子程序27

8.单片机程序28

一、实验内容及目的

1.通过自己设计测温电路板,并用keilc编程算法,使小炉子可达到设定温度,通过优化PID参数,使控制时间尽量短,温度静态误差尽量小,控制精度尽可能高。

2.利用matlab编写串口程序和上位机程序,使温控炉的温度能在matlab上用图像的形式将进行实时监控。

二、实验方案内容

1.温度测量设计

温控炉采用PID控制,需要将炉子的温度反馈到控制器中。

温度测量是实现PID控制必不可少的一个部分,温度测量的精度也直接影响到控制的效果。

测量温度的方法大致有膨胀式、压力式、热电偶、热电阻、辐射式、红外线这几种,本次实验选用热电阻测量温度。

1)温度测量原理

热敏电阻的阻值会随温度的变化而变化,公式如下:

式中RT、RT0分别为温度T、T0时的电阻值,Bn为材料常数。

温度的变化会使热敏电阻的阻值发生变化,而阻值发生变化会使电路的电压和电流发生变化,通过测量电路的电压和电流,就能够间接测量出温度。

2)测温电路设计

测温电路图如下

其中R2是热敏电阻,R3、R1、R4是测温电阻。

温度发生变化时,热敏电阻的阻值会发生变化,使R3两端的电压值发生变化,电压跟随器将R3的电压输出,起到隔离的作用。

输出电压值为

,带入热敏电阻阻值公式可得:

这样便得到了温度和电压的对应关系。

但温度和电压的对应关系并不是线性的,选取合适的R3值,能将温度和电压的对应关系线性化。

选取

时线性程度最好。

3)温度与电压的对应关系

由于电压值、热敏电阻的系数和额定值存在一定的误差,若直接用公式求出温度值,会产生较大的误差。

由于温度值与电压值线性程度较高,可以先测出几个温度值和电压值,再用插值法计算出温度。

调节温控炉的开度,当温度稳定时,记下温控炉的温度和单片机测量的AD值。

R

27.7

43.8

47.9

51.8

64.1

68.9

76.0

83.2

89.5

92.1

AD

187

312

340

375

486

538

594

655

702

732

2.单片机程序设计

1)程序功能

单片机的功能有A/D转换、PID计算、输出方波控制温控炉、数码管显示、串口通讯、执行上位机指令、键盘控制等。

设计程序时分别将各个功能写在子函数中,按照一定的时间顺序循环执行。

程序的控制周期是一秒,单片机先通过P1.0口采集电压值,再将电压值经A/D转换为测量值,PID根据测量值计算出温控炉的开度,并将温度和开度发送到上位机上。

若控制方式为上位机控制,上位机接收到信号后计算出开度发送给单片机,单片机不做PID计算。

程序有三个模式,0模式可以通过按键读、写控制器的控制参数和给定值,并用数码管显示数据。

1模式用单片机控制温控炉,并将数据传输到上位机中,2模式用上位机控制单片机,

2)PID控制程序

a)定点数计算

C51计算浮点数的速度较慢,计算定点数较快,计算PID使用定点数计算。

PID计算公式如下:

e为给定值和测量值的误差,12位定点数(小数点在最高位),32位整形。

r为给定值,12位定点数(小数点在最高位),16位整形。

kp、ki、kd为控制器计算参数,写程序时用KI=ki*dt,KD=kd/dt来替代,KI和KD为16位定点数(小数点在第12位),16位整形。

xp、xi、xd为控制器计算值,28位定点数(小数点在第24位),32位整形。

u为控制器输出值,28位定点数(小数点在第24位),32位整形。

计算时先将r和y归一化,然后乘以4096转换为12位定点数,计算得到12位定点数e。

e与16位控制器参数计算得到28位定点数,小数点在第24位上。

经过非线性饱和处理后,取出第24位到第12位的数据作为12位定点数u的数据。

再将u偏移后转换为温控炉的控制量开度。

b)非线性饱和及偏移

为了抗积分饱和以及防止输出量溢出,加入了两个非线性饱和环节。

当积分项xi积累到4096*4096(既1)时,积分项不再增加,当积分项xd积累到-4096*4096(既-1)时,积分项不再减小。

当u的值大于4096*4096-1(既1)时,u=4096*4096-1,当u的值小于0时,u=0。

加入非线性环节饱和后,PID的输出u总是大于0的,没有负输出,故加入一偏移量0.5,使PID的输出范围由0到1.0变为-0.5到0.5。

3)数码管显示

数码管显示利用视觉暂留原理,每20毫秒只显示一个字符,经过5次显示将4位数码管上的数字显示出来。

数码管刷新的前4次显示4位数据,第5次显示小数点。

数码管显示的4个数据都放在字符数组sdata中,其他程序若要改变显示的数据,直接改写sdata中的内容即可。

数码管能显示16进制数,显示的字符形状放在数组table中。

数码管是否显示由标识enable决定,可在定时器中设定在一段时间内enable为0,一段时间内enable为1来实现数码管的闪烁。

数码管显示刷新的程序放在定时器中,计算耗时长的程序以及按住按键时都能正常显示。

4)串口通信

串口通讯采用异步通讯的方式,波特率为9600,停止位为1位,无校验位。

设置定时器1为8位自动重装模式,装入值为0xFD,设置串口通讯模式为8位数据可变波特率模式,并开启串行口中断。

发送数据时,先关闭串行口中断,发送一位数据,判断位TI为1后,先将TI置0,然后再发送下一位数据,数据发送完成后,开启串行口中断。

接收数据时,先将中断位RI置0,再将数据取出。

与上位机约定终值字符为A,接收到数据A时,数据接受完成的标志变量置1。

5)上位机控制指令的接收和执行

上位机与单片机通过ASCII码通讯。

指令的格式为:

字母=数字,例如r=10。

当上位机发送完数据时,就会发送终值字符A。

单片机先将字符收到字符数组中,并记下接收数据的个数,收到字符A时终止接收数据。

单片机先判断首位字母,当字母为p、i、d时,将参数kp、ki、kd更改为等号后的数据,为m时改变程序的模式,为r时改变给定值,为k时改变开度。

等号后的数据为用字符串表示的整数,将字符减去字符’0’后得到对应的数值,然后再加权相加得到传输的数字。

6)A/D采样

STC12系列的单片机在P1口有A/D转换器,能将0至5V的电压信号转换为10位精度的数值,前8位存在寄存器ADC_RES中,后两位存在ADC_RESL中。

设置P1.0口为A/D采样口,打开A/D转换器电源,选择转换周期为540个时钟周期,将转换位ADC_START置1,选择通道为0口。

读取AD转换时,先将AD转换标志位ADC_FLAG清0,待标志位为1时,取出寄存器中的数据加权相加得到10位精度的A/D转换数值。

7)温度与AD测量值的转换

用得到的10组数据线性插值来计算当前的温度和AD值。

先判断当前值位于哪两组数据之间,再根据以下公式计算:

8)按键扫描

主程序每循环一次就执行一次按键扫描,对于无源键盘,先将前4口置1,后4口置0,延时防抖后读取前4口的数值来判断是哪一行,再将前4口置0,延时防抖后读取后4口的数值来判断是哪一列,通过行列来判断按下的键盘。

并将按纽标志fkey置1。

对于有源键盘,判断其是否为0,若为0,延时10毫秒后再次判断,若再为0,将标志位置1。

标志位置1后有按键释放判断,若按键未释放,则循环判断直到释放为止。

9)按键的功能表

主程序中的按键功能程序判断按键标志位为1后,执行功能表中对应的内容。

程序模式为0时,按键2为减一,按键3为增1,按键6为右移,按键7为左移,按键A为写入数码管上显示的数据,按键B为读取参数数据,按键E和F为改变参数。

按下按键KA进入模式1。

程序模式为1时,矩阵按键无操作,按下按键KA进入模式0。

程序模式2仅能由上位机控制进入,在模式2下按下按键KA进入模式0。

10)PWM方波

温控炉控制端为低电平时加热,控制端为高电平时不加热。

PWM方波的周期为1秒,定时器的周期为0.5毫秒,既一秒执行2000次,所以开度的值为0到2000,当定时器执行次数小于开度时,输出为低电平,当定时器执行次数大于开度时,输出为高电平,从而实现PWM方波控制。

11)多任务处理

程序被放置在主程序中循环,当标志位为1时执行,其中大部分的标志位由定时器来置1。

定时器0每0.5毫秒溢出一次,溢出2000次(1秒)为一周期。

每次溢出均判断是否改变温控炉控制端电平。

每溢出40次显示一位数码管。

每溢出2000次将1秒标志位置1,程序按照AD转换、PID计算、串口通讯的顺序执行。

3.上位机程序设计

1)上位机串口通信

创建串口对象,设置为8位异步通讯模式,波特率为9600,无校验,1位停止位,设置终止字符为A。

当收到终止字符为A时调用子程序PAD。

串口接收到字符串,PAD程序将字符串转换为数值,第一个数值为温度值,第二个数值为开度,并记录在数组u和Y中,绘制出响应曲线。

2)上位机控制

当控制参数kp、ki、kd、给定值r以及模式值mod发生变化时,上位机向单片机发送指令。

当模式值为2时,上位机接收温度数据并向单片机发送控制量开度。

4.PID算法的设计及其优化

1)系统辨识

设置开度为10,用上位机记录下温度变化的曲线。

将曲线做标准化处理后,先用两点法做初步辨识,再用粒子群算法做精确辨识。

2)PSO参数优化

根据辨识得到的参数,使用经验公式计算出大概值,并用PSO算法得到较好的参数。

5.温控炉控制实验

1)单片机控制

设置给定值为50,待系统稳定后加热到70,稳定后再减少到60.

2)上位机控制

设置给定值为50,先用单片机控制,待系统稳定后输入mod=2,转变为上位机控制,系统稳定后加热到70,稳定后再减少到60。

三、实验结果及分析

1.单片机控制

2.上位机控制

稳定时间大约为3分钟,超调量小于10%,静态误差约为0.2度。

采用PID控制具有较好的控制效果。

由于系统散热为自然散热,温度下降较慢,缩短稳定时间要尽可能的减小超调量。

四、实验中遇到的问题

1.在宿舍做系统辨识时受到风扇干扰,响应曲线稳定后出现周期性波动。

2.设计测温电路时,我们尽可能的增大了20度至100度间电压的范围(0.75V至3.25V),但NTC电阻的实际值与额定值有一定误差,温度为93度时NTC的电压达到了3.5V(LM324输入5V时的放大极限)。

在设计电路时应考虑到误差而留有一定的余量。

3.测温电阻原先贴在金属铜片上,测温测到一半时,测温电阻脱离金属片,只能重新测量数据。

4.测量得到的AD、温度曲线与根据公式计算得到的曲线有一定的偏离。

5.上位机发送浮点数时单片机解析数据会出错,强制转换为整形后修复这个问题。

6.MALTAB发送一条数据后会自动发送字符A,而刚开始认为字符A需要自己发送。

7.测量得到的电压值有一定的扰动,辨识时较难判断迟延环节的参数。

8.辨识得到的参数的响应曲线与实际曲线平均相差1度。

9.系统的超调量比仿真的超调量大。

五、附录

1.上位机主程序

clc;

clearall;

closeall;

globalr;

globalr0;

globalmod;

globalmod0;

globalkp;

globalki;

globalkd;

globalu;

globaly;

globals;

globaldt;

globalop;

globalkiu;

globale0;

globalua;

globalch;

globalcc;

globalkaidu;

r=50;

r0=r;

mod=1;

mod0=1;

cc=[];

%kp=22.7299;

%ki=0.0251;

%kd=0.0572;

kp=37.8831;

ki=0.0622;

kd=13.9845;

kiu=0;

e0=0;

y=[];

op=1;

s=serial('COM7','Parity','none','StopBits',1);

set(s,'BaudRate',9600);

s.terminator='A';

s.DataBits=8;

s.InputBufferSize=4096;

s.OutputBufferSize=4096;

s.BytesAvailableFcnMode='terminator';

s.BytesAvailableFcn=@pad;

%s.BreakInterruptFcn

dt=1;

fopen(s);

%pause;

%fclose(s)

%delete(s)

%clears

2.上位机子程序

functionpad(s,event)

globalr;

globalr0;

globalmod;

globalmod0;

globalkp;

globalki;

globalkd;

globalu;

globalop;

globaly;

globaldt;

globalkiu;

globale0;

globalua;

globalkaidu;

globalch;

globalcc;

persistentn;

persistentt;

AD=[187312340375486538594655702732];

TD=[27.743.847.951.864.168.976.083.289.592.1];

ifisempty(n)

n=1;

else

n=n+1;

end

out=fscanf(s);

out=out(1:

end-1);

a=str2num(out);

%fori=1:

10;

%ifAD(i)>a

(1)

%break;

%end

%end

%

%ifi==1

%a

(1)=TD(i)-(TD(i+1)-TD(i))*(AD(i)-a

(1))/(AD(i+1)-AD(i));

%else

%a

(1)=TD(i)-(TD(i)-TD(i-1))*(AD(i)-a

(1))/(AD(i)-AD(i-1));

%end

fori=1:

10

ifTD(i)>r;

break;

end

end

ifi==1

rad=AD(i)-(AD(i+1)-AD(i))*(TD(i)-r)/(TD(i+1)-TD(i));

else

rad=AD(i)-(AD(i)-AD(i-1))*(TD(i)-r)/(TD(i)-TD(i-1));

end

modc=0;

y=[ya

(1)/10];

u=[ua

(2)/20];

t=[tn*dt];

subplot(2,1,1)

plot(t,y);

gridon;

holdon;

title('ζÈy');

subplot(2,1,2)

plot(t,u);

gridon;

holdon;

title('¿ª¶Èu');

ifr~=r0

r0=r;

ch=['r=',num2str(r*10)];

fprintf(s,ch);

end

ifmod~=mod0

mod0=mod;

ch=['m=',num2str(mod)];

fprintf(s,ch);

modc=1;

end

ifmod==2&&modc==0;

pause(0.2);

e=rad-a(3);

kpu=kp*e;

kiu=kiu+ki*e*dt;

kdu=kd*(e-e0)/dt;

e0=e;

ifkiu>4096

kiu=4096;

end

ifkiu<-4096

kiu=-4096;

end

ua=kpu+kiu+kdu+2048;

ifua<0

ua=0;

end

ifua>4096

ua=4096;

end

kaidu=ua/4096*2000-900;

ifkaidu<0;

kaidu=0;

end

ch=['k=',num2str(int32(kaidu))];

fprintf(s,ch);

end

ifop==0

fclose(s)

delete(s)

clears

end

end

3.数据处理程序

clc;

clearall;

closeall;

loaddx3;

Y=y;

u1=0;

u2=20;

Y1=Y(1:

2000);

[lp,m]=size(Y1);

iflp

lp=m;

end

U(1:

lp)=20;

Y2=Y1;

fori=3:

lp-2

Y2(i)=(Y1(i-2)+Y1(i-1)+Y1(i)+Y1(i+1)+Y1(i+2))/5;

end

Y2=de_abnormal(Y2,10);

y0=Y2

(1);

Y3=Y2-y0;

nzero=0;

Y4=Y3(1+nzero:

lp);

U=U(1+nzero:

lp);

t(1:

lp)=0:

lp-1;

t=t*dt;

t2(1:

1481)=0:

1480;

t2=t2*dt;

t1=t(1:

lp-nzero);

%plot(t,Y1);

%holdon;

plot(t1,Y4);

%subplot(2,1,1)

%plot(t2,u)

%subplot(2,1,2)

%plot(t2,y)

Y=Y4;

savedx11Ydtu1u2;

4.系统辨识主程序

clc;

clearall;

closeall;

loaddx11;

Y=Y(10:

end);

TA=clock;

[lp,m]=size(Y);

iflp

lp=m;

end

U(1:

lp)=u2-u1;

Kmax=30;

Kmin=5;

Tmax=500;

Tmin=200;

num=50;

maxv

(1)=(Kmax-Kmin)/10;

maxv

(2)=(Tmax-Tmin)/10;

c1=0.7;

c2=1.4;

c3=1.4;

fori=1:

num

PSO(i,1)=rand()*(Kmax-Kmin)+Kmin;

PSO(i,2)=rand()*(Tmax-Tmin)+Tmin;

PSOV(i,1)=rand()*(Kmax-Kmin)+Kmin;

PSOV(i,2)=rand()*(Tmax-Tmin)+Kmin;

end

bestPSO(1:

num)=10e40;

solpso=10e40;

Q(1:

num)=10e40;

bestq(1:

num)=10e40;

Khi=[];

Thi=[];

forn=1:

3

forab=1:

20

fori=1:

num

Q(i)=QV(Y,U,dt,PSO(i,1),PSO(i,2),n,0);

Khi=[KhiPSO(i,1)];

Thi=[ThiPSO(i,2)];

ifQ(i)

bestq(i)=Q(i);

bestPSO(i,1)=PSO(i,1);

bestPSO(i,2)=PSO(i,2);

end

end

bestp=Q

(1);

fori=2:

num

ifQ(i)

bestp=Q(i);

bestpPSO

(1)=PSO(i,1);

bestpPSO

(2)=PSO(i,2);

end

end

ifbestp

solpso=bestp;

solk=bestpPSO

(1);

solt=bestpPSO

(2);

soln=n;

end

fori=1:

num

PSOV(i,1)=c1*PSOV(i,1)+c2*rand()*(bestPSO(i,1)-PSO(i,1))+c3*rand()*(bestpPSO

(1)-PSO(i,1));

PSOV(i,2)=c1*PSOV(i,2)+c2*rand()*(bestPSO(i,2)-PSO(i,2))+c3*rand()*(bestpPSO

(2)-PSO(i,2));

ifPSOV(i,1)>maxv

(1)

PSOV(i,1)=maxv

(1);

end

ifPSOV(i,2)>maxv

(2)

PSOV(i,2)=maxv

(2);

end

ifPSOV(i,1)<-maxv

(1)

PSOV(i,1)=-maxv

(1);

end

ifPSOV(i,2)

(2)

PSOV(i,2)=-maxv

(2);

end

PSO(i)=PSO(i)+PSOV(i);

ifPSO(i,1)>Kmax

PSO(i,1)=Kmax;

end

ifPSO(i,2)>Tmax

PSO(i,2)=Tmax;

end

ifPSO(i,1)<-Kmax

PSO(i,1)=-kmax;

end

ifPSO(i,2)<-Tmax

PSO(i,2)=-Tmax;

end

end

end

end

time1=etime(clock,TA);

ks=num2str(solk);

Ts=num2str(solt);

ns=num2str(soln);

QBs=num2str(solpso);

text1=['k=',ks,',T=',Ts,',n=',ns,',Q=',QBs];

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 初中教育 > 科学

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

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