您的位置 首页 FPGA

含糊操控算法子程序

程序为模糊控制程序,基于8位单片机,为模糊控制算法程序,实现简单的模糊控制,经实践总结得出,当调整幅度较大时,会出现振荡,系统难以

程序为含糊操控程序,根据8位单片机,为含糊操控算法程序,完成简略的含糊操控,经实践总结得出,当调整起伏较大时,会呈现振动,体系难以到达安稳,这就需求更高一级的算法操控调整,当调整起伏较小时,体系能够很快到达安稳。

以下为含糊算法源程序:
#include “reg52.h”
//————————————————————————————
// 界说间隔输入常量
#define GAP_ZERO 0x00
#define GAP_VSMALL 0x01
#define GAP_SMALL 0x02
#define GAP_MEDIUM 0x03
#define GAP_BIG 0x04
// 界说操控输出常量
#define TURN_ZERO 0x80
#define TURN_VSMALL 0x81
#define TURN_SMALL 0x82
#define TURN_MEDIUM 0x83
#define TURN_BIG 0x84
//————-界说常量—————————————————————-
#define MU_MAX 0XFF //含糊度的最大值为0XFF代外表1
#define RULE_TOT 10 //规矩数个数
#define MF_TOT 5 //成员函数的个数
#define IO_NUM 0x07
#define LABEL_NUM 0x70
#define DEFAULT_VALUE 0x00
//—————-界说数据库———————————————————–
unsigned char code output_memf[MF_TOT]={0, 15, 35, 60, 102};// OUTPUT TURNING NUMBER:
//ZERO, VSMALL, SMALL, MEDIUM, BIG
unsigned char code input_memf[MF_TOT][4]={
// 输入功用函数以点斜式办法存储. 榜首维成员函数标号第二维是点斜式数据
//间隔功用函数
{ 0x00, 0x00, 0x00, 0x0d }, // VSLOW
{ 0x00, 0x0d, 0x14, 0x0d }, // SLOW
{ 0x1e, 0x0d, 0x32, 0x0d }, // MEDIUM
{ 0x3C, 0x0d, 0x50, 0x0d }, // FAST
{ 0x50, 0x09, 0x6e, 0x00 } // VFAST
};
//———–界说含糊体系规矩———————————————————–
unsigned char code rules[RULE_TOT]={
// if… then…
GAP_ZERO,TURN_ZERO,
GAP_VSMALL,TURN_VSMALL,
GAP_SMALL,TURN_SMALL,
GAP_MEDIUM,TURN_MEDIUM,
GAP_BIG,TURN_BIG
};
//———–界说各变量—————————————————————–
unsigned char outputs[MF_TOT],fuzzy_out; //含糊输出mu值
//———–子程序函数头声明———————————————————–
void fuzzy_engine(uchar);
uchar compute_memval(uchar,uchar);
void defuzzify(void);

uchar compute_memval(uchar input,uchar label)
{
int data temp;
if (input < input_memf[label][0])
{ // 假如输入不在曲线下u值为0
return 0;
}
else
{
if (input < input_memf[label][2])
{
temp=input; // 用点斜式核算mu
temp-=input_memf[label][0];
if (!input_memf[label][1])
{
temp=MU_MAX;
}
else
{
temp*=input_memf[label][1];
}
if (temp < 0x100)
{ // 假如成果不超越1
return temp; // 回来核算成果
}
else
{
return MU_MAX; // 保证mu值在范围内
}
}
else
{ // 输入落在第二条斜线上
temp=input; // 用点斜式办法核算 mu
temp-=input_memf[label][2];
temp*=input_memf[label][3];
temp=MU_MAX-temp;
if (temp < 0)
{ // 保证成果不小于0
return 0;
}
else
{
return temp; // mu为正 – 回来成果
}
}
}
return 0;
}

void defuzzify(void)
{
unsigned long numerator, denominator;
unsigned char j;
numerator=0; // 康复总数值
denominator=0;
for (j=0; j { // 核算总和值
numerator+=(outputs[j]*output_memf[j]);
denominator+=outputs[j];
outputs[j]=0; // 清零输出作为参阅运用 }
if (denominator)
{ // 保证分母是0的状况不发生
fuzzy_out=numerator/denominator; // 确认 COG
}
else
{
fuzzy_out=DEFAULT_VALUE; // 没有规矩被触发
}
}
}

unsigned char bdata clause_val; // 保存当时的分支进行快速拜访
sbit clause_type = clause_val^7; // 表明分支是否是条件分支或者是成果分支
void fuzzy_engine(uchar input)
{
bit then; // 当正在剖析成果时置位
unsigned char if_val, // 保存当时规矩中条件分支中的值
clause, // 规矩基中当时的分支
mu, // 保存当时分支中的值
label=0; // 被条件运用的成员函数
then=0; // 设榜首个分支是条件分支
if_val=MU_MAX; // max out mu for the first rule
for (clause=0; clause { // 遍历每条规矩
clause_val=rules[clause]; // 读入当时的分支
if (!clause_type)
{ // 当时的分支是不是条件分支
if (then)
{ // 是否正在剖析成果…
then=0;
if_val=MU_MAX; // 复位mu
}
mu=compute_memval(input, label); // 得到条件分支的值
if_val=mu;
label++;
}
else
{ // 当时分支是成果
then=1; // 置位标志位,假如当时规矩的mu比参阅的值要大,保存这个值作为新的含糊输出
if (outputs[clause_val&0x07] < if_val)
{
outputs[clause_val&0x07]=if_val;
}
}
}
defuzzify(); // 用COG办法核算含糊输出和反含糊输出
}
//——————————————————————————

给出含糊操控的流程图,若想彻底了解清楚其操控原理,最好仍是要找想关的含糊操控理论书本,方能了解透彻:

1.操控理论框图
2.操控算法的总流程图,对应含糊操控算法的程序流程图

声明:本文内容来自网络转载或用户投稿,文章版权归原作者和原出处所有。文中观点,不代表本站立场。若有侵权请联系本站删除(kf@86ic.com)https://www.86ic.net/fangan/fpga/261052.html

为您推荐

联系我们

联系我们

在线咨询: QQ交谈

邮箱: kf@86ic.com

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

返回顶部