PID控制步进电机转速仿真及c程序

  • 格式:docx
  • 大小:55.79 KB
  • 文档页数:8

下载文档原格式

  / 20
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

PID控制步进电机转速仿真及c程序

#include

#include"lcd1602.h"

sfr T2MOD = 0x0c9;

#define uchar unsigned char

#define uint unsigned int

sbit Q0 = P2^4;

sbit Q1 = P2^5;

sbit Q2 = P2^6;

sbit Q3 = P2^7;

sbit PWM= P1^7;

sbit UP= P1^0;

sbit DOWM= P1^1;

sbit GORB= P2^3; //换相

sbit ADDSPEED = P1^2;

sbit SUBSPEED= P1^3;

uint tuint = 65535;

uint tpwm = 1;//pwm周期为10000us tpwm变量表示pwm高电平时间,也相当于占空比(仿真时,频率高时,电机反应慢。在实物上要加大频率)

uchar t1_flag = 0;

uint pulse = 0;

uint t0_flag = 0;

uchar t2_flag = 0;

bit t2_over = 0;

bit Just_Get = 1;

#define ZZ { Q0 = 0;Q1 = 0;Q2 = 1;Q3 = 1;}//正转

#define FZ { Q0 = 1;Q1 = 1;Q2 = 0;Q3 = 0;}//反转

#define STOP{ Q0 = 1;Q1 = 0;Q2 = 1;Q3 = 0;}//停止

//禁止出现Q0 = 0;Q1 = 1;Q2 = 0;Q3 = 1; 不然会烧掉mos管

//************************ PID ************************************* float now = 0,bef = 0,bbef = 0; //本次采样值,上次采样值,上上次采样值float err_now,err_bef,err_bbef;//当前偏差,上次偏差,上上次偏差float error_add = 0;//所有偏差之和

float set = 25;//设定值

float kp = 25;

float ki = 25;

float kd = 0;

//*****************************************************************

void delayms(uint ms)//延时?个ms

{

uchar a,b,c;

while(ms--)

{

for(c=1;c>0;c--)

for(b=142;b>0;b--)

for(a=2;a>0;a--);

}

}

void timer_init()

{

EA = 1;

ET0 = 1;

ET1 = 1;

ET2 = 1;

TMOD = 0x15; //定时器0 计数模式定时器1模式1

T2MOD = 0x01;

TH0 = TL0 = 255;

TH2 = 0x3C;

TL2 = 0xB0;//50MS

}

void timer1() interrupt 3

{

if(t1_flag == 0)

{

t1_flag = 1;

PWM = 1;

TH1 = (tuint - tpwm + 1)/256;

TL1 = (tuint - tpwm + 1)%256;

}

else

{

t1_flag = 0;

PWM = 0;

TH1 = (tuint - 10000 + tpwm + 1)/256;

TL1 = (tuint - 10000 + tpwm + 1)%256;

}

}

void timer0() interrupt 1

{

TH0 = TL0 = 255;

t0_flag++;

}

void timer2() interrupt 5

{

TF2 = 0;

TH2 = 0x3C;

TL2 = 0xB0;//50MS

t2_flag++;

if(t2_flag == 2)

{

TR0 = 0;

TR2 = 0;

t2_flag = 0;

t2_over = 1;//表示100ms时间到

}

}

void GetPulse()

{

t0_flag = 0;

t2_flag = 0;

TH0 = TL0 = 255;

TH2 = 0x3C;

TL2 = 0xB0;//50MS

TR0 = 1;

TR2 = 1;

}

int PID()//增量式PID

{

int change;

err_now = set - now;

err_bef = set - bef;

err_bbef = set - bbef;

change = kp*(err_now - err_bef) + ki*err_now + kd*(err_now - 2*err_bef + err_bbef);

/*

if(set >= now)

{

if(set - now > 1)

change = kp*(err_now -err_bef) + ki*err_now + kd*(err_now -2*err_bef + err_bbef);

else

change = 0.2*kp*(err_now - err_bef) + 0.5*ki*err_now + kd*(err_now - 2*err_bef + err_bbef);

}

else if(now > set)

{

if(now - set > 1)

change = kp*(err_now -err_bef) + ki*err_now + kd*(err_now -2*err_bef + err_bbef);

else

change = 0.2*kp*(err_now - err_bef) + 0.5*ki*err_now + kd*(err_now - 2*err_bef + err_bbef);