📄 fuzwizmask.m
字号:
function fuzwizmask(CB,varargin)
%FUZWIZMASK Initialization for FIS Wizard components.
%
% This function is meant to be called by the FIS Wizard block.
%
% See also FUZBLOCK.
% Authors: P. Gahinet and R. Jang
% Copyright 1994-2002 The MathWorks, Inc.
% $Revision: 1.14 $ $Date: 2002/04/02 21:25:32 $
% Initialization functions for various components
switch get_param(CB,'MaskType')
case 'FIS Wizard'
% FIS Wizard initialization
fis = varargin{1}; % valid FIS at this point
% Store current FIS in block UserData to prevent multiple updates
if ~isequal(fis,get_param(CB,'UserData'))
set_param(gcb,'UserData',fis)
LocalCreateFIS(CB,fis);
end
case 'Input MF Eval'
% Initialize input MF blocks
LocalCreateInputMF(CB,varargin{:});
case 'Output MF Eval'
% Initialize output MF blocks
LocalCreateOutputMF(CB,varargin{:});
case 'FIS Rule'
% Build rule block
LocalCreateRule(CB,varargin{:});
end
%----------------- Local Functions ------------------------------
%%%%%%%%%%%%%%%%%%
% LocalCreateFIS %
%%%%%%%%%%%%%%%%%%
function LocalCreateFIS(CB,fis)
% Builds subsystem representing FIS
load_system('fuzwiz')
% Clear existing FIS (except I/O ports to prevent disconnecting the block
InPort = get_param([CB '/In1'],'handle');
OutPort = get_param([CB '/Out1'],'handle');
AllBlocks = get_param(find_system(CB,'SearchDepth',1,'FollowLinks','on',...
'LookUnderMasks','all','Type','block'),'handle');
AllBlocks = cat(1,AllBlocks{:});
AllBlocks(ismember(AllBlocks,[InPort;OutPort;get_param(CB,'handle')])) = [];
for ct=1:length(AllBlocks)
delete_block(AllBlocks(ct));
end
AllLines = get_param(CB,'lines');
for ct=1:length(AllLines)
delete_line(AllLines(ct).Handle);
end
% FIS parameters
nin = length(fis.input);
nout = length(fis.output);
nrule = length(fis.rule);
isSugeno = strcmpi(fis.type,'sugeno');
% Protect / in input and output names (leads to invalid block path in ADDBLOCK)
for ct=1:nin
fis.input(ct).name = strrep(fis.input(ct).name,'/','//');
end
for ct=1:nout
fis.output(ct).name = strrep(fis.output(ct).name,'/','//');
end
% Draw new FIS
% RE: Positions are [x1 y1 x2 y2] with (0,0) in upper left corner
set_param(InPort,'Position',[30 100 60 115]);
DemuxBlock = sprintf('%s/Demux',CB);
add_block('built-in/Demux',DemuxBlock,'Outputs',num2str(nin),'ShowName','off');
add_line(CB,'In1/1','Demux/1');
% Input MF blocks
y0 = 40;
rule_ant = cat(1,fis.rule.antecedent);
ctTerm = 1;
for ct=1:nin,
Dest = sprintf('%s',fis.input(ct).name);
dy = 16+8*length(fis.input(ct).mf);
add_block('fuzwiz/FIS Input MF',sprintf('%s/%s',CB,Dest),...
'Position',[150 y0 200 y0+dy],...
'MaskValues',{'fis',sprintf('%d',ct)});
add_line(CB,sprintf('Demux/%d',ct),[Dest '/1']);
% Add terminator to unconnected output ports
unused_mf = find(~ismember(1:length(fis.input(ct).mf),rule_ant(:,ct)));
for ctp=1:length(unused_mf)
dyt = 8*unused_mf(ctp);
add_block('built-in/Terminator',sprintf('%s/Term%d',CB,ctTerm),...
'ShowName','off','Position',[220 y0+dyt 230 y0+dyt+10]);
add_line(CB,sprintf('%s/%d',Dest,unused_mf(ctp)),sprintf('Term%d/1',ctTerm));
ctTerm = ctTerm+1;
end
y0 = y0 + dy + 30;
end
set_param(DemuxBlock,'Position',[110 20 115 y0])
% Output MF blocks
y0 = y0 + 30;
rule_conseq = cat(1,fis.rule.consequent);
for ct=1:nout,
Dest = sprintf('%s',fis.output(ct).name);
dy = 16+8*length(fis.output(ct).mf);
add_block('fuzwiz/FIS Output MF',sprintf('%s/%s',CB,Dest),...
'Position',[130 y0 200 y0+dy],...
'MaskValues',{'fis',sprintf('%d',ct)});
if isSugeno & any(strcmpi({fis.output(ct).mf.type},'linear'))
add_line(CB,'In1/1',[Dest '/1']);
end
% Add terminator to unconnected output ports
unused_mf = find(~ismember(1:length(fis.output(ct).mf),rule_conseq(:,ct)));
for ctp=1:length(unused_mf)
dyt = 8*unused_mf(ctp);
add_block('built-in/Terminator',sprintf('%s/Term%d',CB,ctTerm),...
'ShowName','off','Position',[220 y0+dyt 230 y0+dyt+10]);
add_line(CB,sprintf('%s/%d',Dest,unused_mf(ctp)),sprintf('Term%d/1',ctTerm));
ctTerm = ctTerm+1;
end
y0 = y0 + dy + 30;
end
% Defuzz blocks for output MF values (one per output)
InputPortWidth = sum(cat(1,fis.rule.consequent)>0,1);
x0 = 500;
y0 = 50;
yout = zeros(1,nout);
if isSugeno
% Sugeno systems
for ct=1:nout,
MplxBlock = 'Mux';
add_block('built-in/Mux',sprintf('%s/Mux%d',CB,ct),...
'ShowName','off','DisplayOption','bar',...
'Inputs',num2str(InputPortWidth(ct)),...
'Position',[x0 y0 x0+5 y0+20+10*InputPortWidth(ct)]);
yout(ct) = y0+10+5*InputPortWidth(ct);
y0 = y0+50+10*InputPortWidth(ct);
end
elseif nrule==1
% Mamdani system with single rule. Watch for behavior of Sum block on
% single vector input (sums all inputs)
MplxBlock = 'AggMethod';
add_block('built-in/Gain',sprintf('%s/%s',CB,'AggMethod1'),...
'Gain','1','Position',[x0-30 y0 x0 y0+20+10*InputPortWidth]);
yout = y0+10+5*InputPortWidth;
y0 = y0+50+10*InputPortWidth;
else
% Mamdani system
for ct=1:nout,
if strcmp(fis.aggMethod,'max')
MplxBlock = 'AggMethod';
add_block('built-in/MinMax',sprintf('%s/%s%d',CB,'AggMethod',ct),...
'Function','max','Inputs',num2str(InputPortWidth(ct)),...
'Position',[x0-30 y0 x0 y0+20+10*InputPortWidth(ct)]);
elseif strcmp(fis.aggMethod,'sum')
MplxBlock = 'AggMethod';
symb = '+';
for id = 1:InputPortWidth(ct) - 1
symb = sprintf('+%s',symb);
end
add_block('built-in/Sum',sprintf('%s/%s%d',CB,'AggMethod',ct),...
'Inputs',symb, 'iconshape','rectangular', ...
'Position',[x0-30 y0 x0 y0+20+10*InputPortWidth(ct)]);
elseif strcmp(fis.aggMethod,'probor')
MplxBlock = 'Mux';
probor_system_path = sprintf('%s/%s%d',CB,'AggMethod',ct);
% Add a mux to accept all inputs and pass them into subsystem block
add_block('built-in/Mux',sprintf('%s/Mux%d',CB,ct),...
'ShowName','off','DisplayOption','bar',...
'Inputs',num2str(InputPortWidth(ct)),...
'Position',[x0-50 y0 x0-45 y0+20+10*InputPortWidth(ct)]);
% Add a subsystem block in which to build the probor rule aggregation
add_block('built-in/Subsystem', probor_system_path,...
'Position',[x0 y0 x0+50 y0+20+10*InputPortWidth(ct)], ...
'MaskDisplay','disp(''Probor\n System'')');
% Call the probor rule aggregation method
LocalProborAggMethod( InputPortWidth(ct), probor_system_path);
add_line(CB, sprintf('Mux%d/1',ct), sprintf('AggMethod%d/1',ct));
end
yout(ct) = y0+10+5*InputPortWidth(ct);
y0 = y0+50+10*InputPortWidth(ct);
end
end
% Total firing strength
TFS = sprintf('Total Firing\nStrength');
add_block('built-in/Sum',[CB '/' TFS],...
'Inputs',num2str(nrule),...
'Position',[x0 y0 x0+20 y0+20+10*nrule]);
xytfs = [x0 y0+10+5*nrule];
% Add rule blocks
x0 = 300;
y0 = 30;
mplxport = ones(1,nout);
for ct=1:nrule,
Rule = fis.rule(ct);
nantec = length(find(Rule.antecedent));
nconseq = length(find(Rule.consequent));
dym1 = 8+8*nantec;
dym2 = 8+8*nconseq;
dyr = max(0,(dym1+dym2+5)/2-20);
% Mux rule antecedents and consequents
aMux = sprintf('aMux%d',ct);
add_block('built-in/Mux',[CB '/' aMux],'Inputs',num2str(nantec),...
'ShowName','off','DisplayOption','bar',...
'Position',[x0 y0 x0+5 y0+dym1]);
cMux = sprintf('cMux%d',ct);
add_block('built-in/Mux',[CB '/' cMux],'Inputs',num2str(nconseq),...
'ShowName','off','DisplayOption','bar',...
'Position',[x0 y0+dym1+5 x0+5 y0+dym1+dym2+5]);
% Rule block
RuleBlock = sprintf('Rule%d',ct);
add_block('fuzwiz/FIS Rule',sprintf('%s/%s',CB,RuleBlock),...
'Position',[x0+30 y0+dyr x0+80 y0+dyr+40],...
'MaskValues',{'fis',sprintf('%d',ct)});
% Demux rule outputs
cDemux = sprintf('cDemux%d',ct);
add_block('built-in/Demux',[CB '/' cDemux],'Outputs',num2str(nconseq),...
'ShowName','off','Position',[x0+100 y0 x0+105 y0+dym1]);
% Wiring
add_line(CB,[aMux '/1'],[RuleBlock '/1'])
add_line(CB,[cMux '/1'],[RuleBlock '/2'])
add_line(CB,[RuleBlock '/1'],[cDemux '/1'])
% Wire antecedents
ctport = 1;
for ctin=find(Rule.antecedent),
add_line(CB,...
sprintf('%s/%d',fis.input(ctin).name,Rule.antecedent(ctin)),...
sprintf('%s/%d',aMux,ctport));
ctport = ctport+1;
end
% Wire consequents and outputs
ctport = 1;
for ctout=find(Rule.consequent),
add_line(CB,sprintf('%s/%d',fis.output(ctout).name,Rule.consequent(ctout)),...
sprintf('%s/%d',cMux,ctport));
add_line(CB,sprintf('%s/%d',cDemux,ctport),...
sprintf('%s%d/%d',MplxBlock,ctout,mplxport(ctout)));
ctport = ctport+1;
mplxport(ctout) = mplxport(ctout)+1;
end
% Wire FS outputs
add_line(CB,[RuleBlock '/2'],sprintf('%s/%d',TFS,ct));
y0 = y0 + dym1 + dym2 + 30;
end
% Defuzzification stage
x0 = 580;
if isSugeno
% Sugeno-> library block supporting wtaver and wtsum (inputs = MF values + FS)
switch lower(fis.defuzzMethod)
case 'wtsum'
for ct=1:nout,
Dest = sprintf('Defuzzification%d',ct);
add_block('fuzwiz/wtsum Defuzz',sprintf('%s/%s',CB,Dest),...
'Position',[x0 yout(ct)-15 x0+50 yout(ct)+15]);
add_line(CB,sprintf('%s%d/1',MplxBlock,ct),[Dest '/1']);
end
case 'wtaver'
for ct=1:nout,
Dest = sprintf('Defuzzification%d',ct);
add_block('fuzwiz/wtaver Defuzz',sprintf('%s/%s',CB,Dest),...
'Position',[x0 yout(ct)-15 x0+50 yout(ct)+15]);
add_line(CB,sprintf('%s%d/1',MplxBlock,ct),[Dest '/1']);
add_line(CB,[TFS '/1'],[Dest '/2']);
end
end
else
% Mamdani
for ct=1:nout,
Dest = sprintf('Defuzzification%d',ct);
add_block('fuzwiz/Centroid of Area',sprintf('%s/%s',CB,Dest),...
'Position',[x0 yout(ct)-15 x0+50 yout(ct)+15],...
'MaskValues',{sprintf('fis.output(%d).range',ct)});
% Connect the aggMethod to the defuzz block
add_line(CB,sprintf('AggMethod%d/1',ct),[Dest '/1']);
end
end
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -