问题背景:请科学上网
import numpy as np
from sklearn.metrics import recall_score
from sklearn.preprocessing import MinMaxScaler
from collections import OrderedDict
from math import sqrt
class TOPSIS():
def __init__(self, data, weight = None):
self.data = data
self.normalizedDecision()
if(weight == None):
self.weight = [1. / self.data.shape[1] for x in range(self.data.shape[1])]
else:
self.weight = weight
self.weightCal()
self.bigAndSmallCal()
self.getScore()
# 正则化
def normalizedDecision(self):
for col in range(self.data.shape[1]): # 列数
sum = 0
for row in range(self.data.shape[0]): # 行数
sum += self.data[row, col] * self.data[row, col]
sum = sqrt(sum)
for row in range(self.data.shape[0]): # 行数
self.data[row, col] = self.data[row, col] * 1.0 / sum
# print(self.data)
# 加上权重
def weightCal(self):
for row in range(self.data.shape[0]):
for col in range(self.data.shape[1]):
self.data[row, col] *= self.weight[col]
print(self.data)
# 有时候是要极大值,有时候是要极小值
def bigAndSmallCal(self):
best = np.max(self.data, axis=0)
worst = np.min(self.data, axis=0)
best[0], worst[0] = worst[0], best[0] # 因为价格指标越小越好,所以best应该是个极小值
self.S = []
for row in range(self.data.shape[0]):
best_sum = 0
worst_sum = 0
for col in range(self.data.shape[1]):
best_sum += (self.data[row, col] - best[col]) * (self.data[row, col] - best[col])
worst_sum += (self.data[row, col] - worst[col]) * (self.data[row, col] - worst[col])
best_sum = sqrt(best_sum)
worst_sum = sqrt(worst_sum)
self.S.append([best_sum, worst_sum])
self.S = np.array(self.S)
# 根据公式计算分数,这就是最终的权重
def getScore(self):
self.score = []
for row in range(self.S.shape[0]):
self.score.append(self.S[row][1] / (self.S[row][0] + self.S[row][1]))
self.score = np.array(self.score)
if __name__ == '__main__': # 价格 内存 相机 外观
X = [[250., 16., 12., 5.],
[200., 16., 8., 3.],
[300., 32., 16., 4.],
[275., 32., 8., 4.],
[225., 16., 16., 2.]]
X = np.array(X)
tp = TOPSIS(X)
print(tp.score)