Intensive lectures on practical application cases of MATLAB algorithms-[Intelligent Optimization Algorithms] Multi-objective Algorithm Performance Evaluation Index

foreword

When evaluating the effect of multi-objective optimization algorithms, we usually use five main indicators: GD (Generational Distance), IGD (Inverted Generational Distance), Hypervolume, Spacing and Spread.

GD and IGD are indicators used to measure the distance between the solution set generated by the algorithm and the real frontier solution. Specifically, GD measures the average Euclidean distance between all generated solutions and the true frontier solution, while IGD measures the average Euclidean distance between all true frontier solutions and the generated solution. The goal of these two indicators is that the smaller the better, that is, the generated solution set of the algorithm should be as close as possible to the real frontier solution.

Hypervolume is an indicator used to measure the volume of the real frontier solution that the solution set generated by the algorithm can cover. The goal is that the bigger the better, that is, the solution set generated by the algorithm should cover as many real frontier solutions as possible.

Spacing and Spread are indicators used to measure the distribution of the solution set generated by the algorithm. Spacing measures the minimum Euclidean distance between all solutions, while Spread measures the maximum Euclidean distance between all solutions.

Through comprehensive evaluation of these indicators, we can better understand the performance of the algorithm and optimize it.

Code

MATLAB

Spread.m

%% PopObj:算法求得的pareto解集
%% PF:真实的解集
function Score = Spread(PopObj,PF)
Dis1  = pdist2(PopObj,PopObj);
Dis1(logical(eye(size(Dis1,1)))) = inf;
[~,E] = max(PF,[],1);PF(E,:)
Dis2  = pdist2(PF(E,:),PopObj);
d1    = sum(min(Dis2,[],2));
d2    = mean(min(Dis1,[],2));
Score = (d1+sum(abs(min(Dis1,[],2)-d2))) / (d1+(size(PopObj,1)-size(PopObj,2))*d2);
end

Spacing.m

%% PopObj:算法求得的pareto解集
%% PF:真实的解集
function Score = Spacing(PopObj,PF)
Distance = pdist2(PopObj,PopObj,'cityblock');
    Distance(logical(eye(size(Distance,1)))) = inf;
    Score    = std(min(Distance,[],2));
end

IGD.m

%% PopObj:算法求得的pareto解集
%% PF:真实的解集
function Score = IGD(PopObj,PF)
Distance = min(pdist2(PF,PopObj),[],2);
Score    = mean(Distance);
end

HV.m

%% PopObj:算法求得的pareto解集
%% PF:真实的解集
function [Score,PopObj] = HV(PopObj,PF)
% Hypervolume
[N,M]  = size(PopObj);
fmin   = min(min(PopObj,[],1),zeros(1,M));
fmax   = max(PF,[],1);
PopObj = (PopObj-repmat(fmin,N,1))./repmat((fmax-fmin)*1.1,N,1);
PopObj(any(PopObj>1,2),:) = [];
% The reference point is set to (1,1,...)
RefPoint = ones(1,M);
if isempty(PopObj)
    Score = 0;
elseif M < 4
    % Calculate the exact HV value
    pl = sortrows(PopObj);
    S  = {1,pl};
    for k = 1 : M-1
        S_ = {};
        for i = 1 : size(S,1)
            Stemp = Slice(cell2mat(S(i,2)),k,RefPoint);
            for j = 1 : size(Stemp,1)
                temp(1) = {cell2mat(Stemp(j,1))*cell2mat(S(i,1))};
                temp(2) = Stemp(j,2);
                S_      = Add(temp,S_);
            end
        end
        S = S_;
    end
    Score = 0;
    for i = 1 : size(S,1)
        p     = Head(cell2mat(S(i,2)));
        Score = Score + cell2mat(S(i,1))*abs(p(M)-RefPoint(M));
    end
else
    % Estimate the HV value by Monte Carlo estimation
    SampleNum = 1000000;
    MaxValue  = RefPoint;
    MinValue  = min(PopObj,[],1);
    Samples   = unifrnd(repmat(MinValue,SampleNum,1),repmat(MaxValue,SampleNum,1));
    if gpuDeviceCount > 0
        % GPU acceleration
        Samples = gpuArray(single(Samples));
        PopObj  = gpuArray(single(PopObj));
    end
    for i = 1 : size(PopObj,1)
        drawnow();
        domi = true(size(Samples,1),1);
        m    = 1;
        while m <= M && any(domi)
            domi = domi & PopObj(i,m) <= Samples(:,m);
            m    = m + 1;
        end
        Samples(domi,:) = [];
    end
    Score = prod(MaxValue-MinValue)*(1-size(Samples,1)/SampleNum);
end
end

function S = Slice(pl,k,RefPoint)
p  = Head(pl);
pl = Tail(pl);
ql = [];
S  = {};
while ~isempty(pl)
    ql  = Insert(p,k+1,ql);
    p_  = Head(pl);
    cell_(1,1) = {abs(p(k)-p_(k))};
    cell_(1,2) = {ql};
    S   = Add(cell_,S);
    p   = p_;
    pl  = Tail(pl);
end
ql = Insert(p,k+1,ql);
cell_(1,1) = {abs(p(k)-RefPoint(k))};
cell_(1,2) = {ql};
S  = Add(cell_,S);
end

function ql = Insert(p,k,pl)
flag1 = 0;
flag2 = 0;
ql    = [];
hp    = Head(pl);
while ~isempty(pl) && hp(k) < p(k)
    ql = [ql;hp];
    pl = Tail(pl);
    hp = Head(pl);
end
ql = [ql;p];
m  = length(p);
while ~isempty(pl)
    q = Head(pl);
    for i = k : m
        if p(i) < q(i)
            flag1 = 1;
        else
            if p(i) > q(i)
                flag2 = 1;
            end
        end
    end
    if ~(flag1 == 1 && flag2 == 0)
        ql = [ql;Head(pl)];
    end
    pl = Tail(pl);
end
end

function p = Head(pl)
if isempty(pl)
    p = [];
else
    p = pl(1,:);
end
end

function ql = Tail(pl)
if size(pl,1) < 2
    ql = [];
else
    ql = pl(2:end,:);
end
end

function S_ = Add(cell_,S)
n = size(S,1);
m = 0;
for k = 1 : n
    if isequal(cell_(1,2),S(k,2))
        S(k,1) = {cell2mat(S(k,1))+cell2mat(cell_(1,1))};
        m = 1;
        break;
    end
end
if m == 0
    S(n+1,:) = cell_(1,:);
end
S_ = S;
end

GD.m

%% PopObj:算法求得的pareto解集
%% PF:真实的解集
function Score = GD(PopObj,PF)
% Generational distance
    Distance = min(pdist2(PopObj,PF),[],2);
    Score  = norm(Distance) / length(Distance);
end

Guess you like

Origin blog.csdn.net/qq_36130719/article/details/130145093