非支配快速排序算法详解

非支配快速排序算法详解

对NSGA-II的一个学习记录
         在这里插入图片描述

为易于理解,只用三个点举例子。

Np=3;                       %三个点
current_vector = [1:1:Np]'; %当前向量
current_pf=1;               %先找F1
RANK = zeros(Np,1);         %RANK初始化
all_perm = [repmat([1:1:Np]',Np',1), reshape(repmat([1:1:Np],Np,1),Np^2,1)];%生成两列
all_perm(all_perm(:,1)==all_perm(:,2),:) = [];                              %每个点和其余比较
d=[0 1 0 0 1 1];            %假设支配关系
dominated_particles = unique(all_perm(d==1,2));%依次找到各个点是否受人支配,不在乎受几个人支配,只要受人支配了,那他就不是当前要找的等级。
non_dom_idx = ~ismember(current_vector,dominated_particles);%找到非支配的点的位置,这是一个逻辑值
RANK(current_vector(non_dom_idx)) = current_pf;             %让这些位置成为当前等级
all_perm(ismember(all_perm(:,1),current_vector(non_dom_idx)),:) = [];%找到以后,删除,因为一个点只能属于一个等级
all_perm(ismember(all_perm(:,2),current_vector(non_dom_idx)),:) = [];%找到以后,删除,因为一个点只能属于一个等级
current_vector(non_dom_idx) = [];%当前向量中删除那些非支配点                         
current_pf = current_pf + 1;     %等级+1,找下一个等级。

在这里插入图片描述
在这里插入图片描述
思路以及程序实现过程即为上述。其实在非支配快速排序中还要判断是否已经把所有粒子给分好等级了。有两个跳出循环的地方
1、判断当前向量中是否只有一个点了,要是就一个点了,那他就是最后一个等级了,直接跳出就好了;
2、判断当前向量中,是否没有更多空间去放等级了。(没看太明白,这块直接跳出了,等级也没加,可能就是一个判断的过程。)不影响分等级。

有两个函数,快速非支配排序和比较函数

function [RANK] = FastNonDominatedSorting_Vectorized(fitness)
    % Initialization
    Np = size(fitness,1);
    RANK = zeros(Np,1);
    current_vector = [1:1:Np]';
    current_pf = 1;
    all_perm = [repmat([1:1:Np]',Np',1), reshape(repmat([1:1:Np],Np,1),Np^2,1)];
    all_perm(all_perm(:,1)==all_perm(:,2),:) = []; %每个个体去和别人比。  一个个体有两个目标函数值
    
    % Computing each Pareto Front
    while ~isempty(current_vector)                 %非空,就是我这100个个体还没分完等级呢。
        
        % Check if there is only a single particle
        if length(current_vector) == 1
            RANK(current_vector) = current_pf;
            break;
        end
        
        % Non-dominated particles
            % Note: nchoosek has an exponential grow in computation time, so
            % it's better to take all the combinations including repetitions using a
            % loops (quasi-linear grow) or repmats (linear grow)
            %all_perm = nchoosek(current_vector,2);   
            %all_perm = [all_perm; [all_perm(:,2) all_perm(:,1)]];     
        d = dominates(fitness(all_perm(:,1),:),fitness(all_perm(:,2),:));
        %d是一个逻辑值,他判断了所有个体和单个个体的支配关系。第一列是2到200,第二列全是1,先判断2到200是不是支配了1。以此类推。
        
        
        dominated_particles = unique(all_perm(d==1,2)); 
        % 找到被人支配的,unique就是不管是谁支配了1,不管有几个,我只计数一个
        

        % Check if there is no room for more Pareto Fronts
        if sum(~ismember(current_vector,dominated_particles)) == 0
            break;
        end

        % Update ranks and current_vector  更新等级
        non_dom_idx = ~ismember(current_vector,dominated_particles); %找出那些没有人支配的所在的位置,然后在current_vector中挑出来,就是第一等级
        RANK(current_vector(non_dom_idx)) = current_pf;              %把这些定为第一等级,其余位置都是0,我不在乎他是第几等级。用逻辑值来判断
        all_perm(ismember(all_perm(:,1),current_vector(non_dom_idx)),:) = [];
        all_perm(ismember(all_perm(:,2),current_vector(non_dom_idx)),:) = [];%判断完的就把剔除出去
        current_vector(non_dom_idx) = [];                                    %判断完的就剔除出去了
        current_pf = current_pf + 1;                                         %找下一等级的去,知道找完了才停下来。
    end
end
% Function that returns true if x dominates y and false otherwise
function d = dominates(x,y)
    d = (all(x<=y,2) & any(x<y,2));
end

只是记录学习,如有错误,请及时指出,谢谢大家。

参考:mathworks NSGA-II(2019年更新的那版)

这是一个用于快速支配排序(Fast Non-Dominated Sorting)的基本示例的Matlab代码: ```matlab function [fronts, ranks] = fastNonDominatedSort(population) n = size(population, 1); % 初始化每个个体的支配数量和被支配集合 dominationCount = zeros(n, 1); dominatedSet = cell(n, 1); % 初始化每个个体的等级为0 ranks = zeros(n, 1); % 初始化第一个前沿的空集合 fronts{1} = []; % 计算每个个体的支配数量和被支配集合 for i = 1:n p = population(i, :); for j = 1:n if i == j continue; end q = population(j, :); if dominates(p, q) dominatedSet{i} = [dominatedSet{i}, j]; elseif dominates(q, p) dominationCount(i) = dominationCount(i) + 1; end end % 如果个体i不被任何其他个体支配,则将其添加到第一个前沿中 if dominationCount(i) == 0 ranks(i) = 1; fronts{1} = [fronts{1}, i]; end end % 生成其他前沿 frontIndex = 1; while ~isempty(fronts{frontIndex}) nextFront = []; for i = fronts{frontIndex} for j = dominatedSet{i} dominationCount(j) = dominationCount(j) - 1; if dominationCount(j) == 0 ranks(j) = frontIndex + 1; nextFront = [nextFront, j]; end end end frontIndex = frontIndex + 1; fronts{frontIndex} = nextFront; end end function result = dominates(p, q) result = all(p <= q) && any(p < q); end ``` 这段代码实现了快速支配排序算法,它将输入的种群(population)进行排序,并返回每个个体的等级(ranks)和每个前沿(fronts)中的个体索引。其中,`dominates`函数用于判断一个个体是否支配另一个个体。请注意,此代码仅适用于二维目标优化问题,如果需要处理更高维度的问题,可能需要进行适当的修改。
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

勉为其难免免

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值