学习笔记

数学建模算法:层次分析法

发布于 2023/08/22 · 3 分钟阅读

文章目录

    模型定位

    层次分析法「The analytic hierarchy process」是在对复杂的决策问题的本质、影响因素及其内在关系等进行深入分析的基础上,利用较少的定量信息使决策的思维过程数学化,从而为多目标、多准则或无结构特性的复杂决策问题提供简便的决策方法

    模型共分为三个层级:

    • 目标层:结果输出层,确定目标是什么?
    • 准则层:影响因素集,决定这一结果的因素有什么?
    • 方案层:备选集,从哪些样本中选择?

    模型适用于评价类、排名类、决策类问题

    模型流程

    数据预处理

    在计算中,需要将不同准则的数量级统一,这个过程称为归一化,将一组统一标准的数据视为列向量,把数据化为在总数中的占比即可,范围为(0,1): $$ x_i = \frac{x_i}{\sum_{k=1}^nx_k}\ ,\ i\in{1,2,\dots,n} $$

    生成判断矩阵

    两两比较每个准则(指标)的重要性,记为$a_{ij}$, 来表示相对于指标j,指标i的重要性,且满足: $$ a_{ij} = \frac{1}{a_{ji}} $$

    $a_{ij}$ 含义
    1 指标$i$与指标$j$相同重要
    3 指标$i$比指标$j$稍微重要
    5 指标$i$比指标$j$明显重要
    7 指标$i$比指标$j$强烈重要
    9 指标$i$比指标$j$极端重要

    注:2,4,6,8表示在两者之间

    一致性检验

    由于重要性的比较是单看两者的主观评价,结果不可避免会产生矛盾,我们虽然不能追求完美一致,但是这一判断矩阵必须通过一致性检验,确保重要性差异较为一致: $$ CR = \frac{CI}{RI} , CI = \frac{\lambda_{max}-n}{n-1} $$ 其中$\lambda_{max}$为判断矩阵的最大特征值,$RI$为常数,在不同因素数下有不同取值:

    n 1 2 3 4 5 6 7 8 9 10
    RI 0 0 0.52 0.89 1.12 1.26 1.36 1.41 1.46 1.49
    • 若$CR \leq 0.1 $ : 通过一致性检验
    • 若$CR > 0.1 $ : 重新生成判断矩阵
    权重矩阵
    1. 矩阵按列归一化:即每个数值除以所在列的和
    2. 每行求平均降维即可

    代码实现

    Python Version
    import numpy as np
    
    # 准则重要性矩阵
    A = np.array([[1, 2, 3, 5],
                 [1 / 2, 1, 1 / 2, 2],
                 [1 / 3, 2, 1, 2],
                 [1 / 5, 1 / 2, 1 / 2, 1]])
    [n, m] = A.shape
    
    # 一致性检验
    V, D = np.linalg.eig(A)
    
    maxlam = np.max(V)
    CI = (maxlam - n) / (n - 1)
    RI = [0, 0, 0.58, 0.9, 1.12, 1.24, 1.32, 1.41, 1.45, 1.49, 1.52, 1.54, 1.56, 1.58, 1.59]
    # 判断是否通过一致性检验
    CR = CI / RI[n - 1]
    if CR >= 0.1:
        print('没有通过一致性检验\n')
    else:
        print('通过一致性检验\n')
    
    # 计算权重
    Asum = np.sum(A, axis=0)
    Aprogress = A/(np.ones((n, 1), dtype=np.int64) * Asum)
    
    W = np.average(Aprogress, axis=1)
    Matlab Version
    %输入判断矩阵
    A = [1 2 3 5
        1/2 1 1/2 2
        1/3 2 1 2
        1/5 1/2 1/2 1];
    
    %一致性检验
    maxlam = max(eig(A));
    [~, n] = size(A);
    RI = [0,0,0.58,0.9,1.12,1.24,1.32,1.41,1.45, 1.49, 1.52, 1.54, 1.56, 1.58, 1.59];
    CI = (maxlam - n) / (n-1);
    CR = CI / RI(n);
    if CR < 0.10
        disp('通过一致性检验')
    else
        disp('不通过一致性检验')
        return  % 终止运行 
    end
    
    
    %计算权重向量
    [n,~] = size(A);
    Asum = sum(A,1);    % 按列求和
    Aprogress = A./(ones(n,1)*Asum);
    
    W = sum(Aprogress, 2)./n;