import numpy as np  # 导入numpy包并将其命名为np

# 定义正向化的函数

def positivization(x, type, i):
    '''
    对数据进行正向化处理

    参数:
        x:需要正向化处理的指标对应的原始向量
        typ:指标类型(1:极小型,2:中间型,3:区间型)
        i:正在处理的是原始矩阵的哪一列
    
    返回值:
        posit_x: 正向化后的向量
    '''
    if type == 1:  # 极小型
        print(f'第 {i} 列是极小型,正向化中...')
        posit_x = x.max(0)-x
        print(f'第 {i} 列极小型处理完成')
        print('--------------------------分隔--------------------------')
        return posit_x
    elif type == 2:  # 中间型
        print(f'第 {i} 列是中间型')
        best = int(input('请输入最佳值:'))
        m = (abs(x-best)).max()
        posit_x = 1-abs(x-best)/m
        print(f'第 {i} 列中间型处理完成')
        print('--------------------------分隔--------------------------')
        return posit_x
    elif type == 3:  # 区间型
        print(f'第 {i} 列是区间型')
        a, b = [int(l) for l in input('按顺序输入最佳区间的左右界,并用逗号隔开:').split(',')]
        m = (np.append(a-x.min(), x.max()-b)).max()
        x_row = x.shape[0]  # 获取x的行数
        posit_x = np.zeros((x_row, 1), dtype=float)
        for r in range(x_row):
            if x[r] < a:
               posit_x[r] = 1-(a-x[r])/m
            elif x[r] > b:
               posit_x[r] = 1-(x[r]-b)/m
            else:
               posit_x[r] = 1
        print(f'第 {i} 列区间型处理完成')
        print('--------------------------分隔--------------------------')
        return posit_x.reshape(x_row)

# 第一步:从外部导入数据
# 注:保证表格不包含除数字以外的内容
try:
    x_mat = np.loadtxt('river.csv', encoding='UTF-8-sig', delimiter=',')  # 推荐使用csv格式文件
except FileNotFoundError:
    print('错误:文件 river.csv 未找到,请检查文件路径。')
    exit()

# 第二步:判断是否需要正向化
n, m = x_mat.shape
print(f'共有 {n} 个评价对象 {m} 个评价指标')
judge = int(input('指标是否需要正向化处理,需要请输入1,不需要则输入0:'))
if judge == 1:
    position = np.array([int(i) for i in input('请输入需要正向化处理的指标所在的列,例如第1、3、4列需要处理,则输入1,3,4').split(',')])
    position = position-1
    typ = np.array([int(j) for j in input('请按照顺序输入这些列的指标类型(1:极小型,2:中间型,3:区间型)格式同上').split(',')])
    for k in range(position.shape[0]):
        x_mat[:, position[k]] = positivization(x_mat[:, position[k]], typ[k], position[k])
    print(f'正向化后的矩阵:\n {x_mat}')

# 第三步:对正向化后的矩阵进行标准化
tep_x1 = (x_mat * x_mat).sum(axis=0)  # 每个元素平方后按列相加
tep_x2 = np.tile(tep_x1, (n, 1))  # 将矩阵tep_x1平铺n行
Z = x_mat / ((tep_x2) ** 0.5)  # Z为标准化矩阵
print(f'标准化后的矩阵为:\n {Z}')

# 第四步:计算与最大值和最小值的距离,并算出得分
tep_max = Z.max(0)  # 得到Z中每列的最大值
tep_min = Z.min(0)  # 每列的最小值
tep_a = Z - np.tile(tep_max, (n, 1))  # 将tep_max向下平铺n行,并与Z中的每个对应元素做差
tep_i = Z - np.tile(tep_min, (n, 1))  # 将tep_max向下平铺n行,并与Z中的每个对应元素做差
D_P = ((tep_a ** 2).sum(axis=1)) ** 0.5  # D+与最大值的距离向量
D_N = ((tep_i ** 2).sum(axis=1)) ** 0.5
S = D_N / (D_P + D_N)  # 未归一化的得分
std_S = S / S.sum(axis=0)
sorted_S = np.sort(std_S, axis=0)
print(f'标准化后的得分为:\n {std_S}')  # 打印标准化后的得分

# 结果输出到std_S.csv文件
std_S.to_csv('std_S.csv')

这段代码实现了TOPSIS算法,并通过读取river.csv文件中的数据进行评估,最终将结果保存到std_S.csv文件中。

解决FileNotFoundError错误:

代码中出现的FileNotFoundError: river.csv not found.错误是由于代码找不到river.csv文件导致的。

为了解决这个问题,需要确保以下几点:

  1. 确认文件名和文件路径: 确保river.csv文件名正确,并且该文件位于代码执行的同一目录下,或者提供文件的完整路径。
  2. 检查文件扩展名: 确保文件扩展名确实是.csv,而不是其他扩展名,例如.txt
  3. 检查文件是否位于当前工作目录: 可以使用os.getcwd()函数获取当前工作目录,并使用os.listdir()函数列出当前目录下的文件,确认river.csv文件是否存在。

通过检查以上几点,并进行相应的修改,就可以解决FileNotFoundError错误,并成功运行代码。

Python实现TOPSIS算法进行数据评估与决策

原文地址: https://www.cveoy.top/t/topic/33E 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录