- 有趣的故事,每年学院评奖的时候,都会有许许多多狗血的剧情。。
- 综测规则? 德育成绩*0.5+智育成绩+劳育成绩+体育成绩+美育成绩+特别奖励分数
- 德育成绩满分 100 分
- 智育成绩满分? 20? 分
- 劳育成绩满分? 10? 分
- 体育成绩满分? 10? 分
- 美育成绩满分? 10? 分
- 特别奖励分数? ?无上限
- 分析数据(Pandas)
import xlrd as xl
from bunch import *
Data1 = Bunch()
Data2 = Bunch()
Data3 = Bunch()
data1 = xl.open_workbook("1.xls")
data2 = xl.open_workbook("2.xls")
data3 = xl.open_workbook("3.xls")
work_sheet1 = data1.sheets()[0]
work_sheet2 = data2.sheets()[0]
work_sheet3 = data3.sheets()[0]
all_rows1 = work_sheet1.nrows
all_rows2 = work_sheet2.nrows
all_rows3 = work_sheet3.nrows
all_cols1 = work_sheet1.ncols
all_cols2 = work_sheet2.ncols
all_cols3 = work_sheet3.ncols
- 讲个有趣的事情,为什么我们不选用更高效的方法,而是建立这么多变量呢?
- 解决方法一:建立一个线性列表
- 解决方法二:
-
list0,list1,list2,list3 = [],[],[],[]
start = "list"
for i in range(4):
c = start + str(i)
eval(c).append(1)
print("list0",end=" ")
print(list0)
>>>list0 [1]
你看,这个eval()函数就很好。
- sklearn 模块
- 话说,为什么要用sklearn模块呢??好问题,难道你想从头搭建吗?博主数学不好。博主还很担心他的工程数学数值计算呢?笑死,复变函数都快挂了。。
- 线性回归
- 突然想起来应该介绍一下我们的数据,不然在操作的部分会有些看不懂,但是,不介绍并不特别重要。你可能需要带点想象,比如第一列是性别,第二列是学号,第三列是班级号啥的
- Bunch 模块
- 用它习惯了。机器学习中特别需要这个模块,用起来很方便,就像字典一样。
feature = []
for i in range(1,all_rows1):
d = []
for j in range(3,all_cols1-2):
d.append(work_sheet1.cell_value(i,j))
feature.append(d)
Data1["feature"] = feature
target = []
for i in range(1,all_rows1):
target.append(work_sheet1.cell_value(i,all_cols1-2))
Data1["target"] = target
- ?LinearRegression模块
- 以直线拟合(游戏规则说明了,变量之间是没有相互作用的。)
-
from sklearn.linear_model import LinearRegression
regression = LinearRegression()
model = regression.fit(Data1["feature"],Data1["target"])
print("1 model.intercept_",end = " ")
print(model.intercept_)
print("model.coef_",end=" ")
print(model.coef_)
- 输出结果
- 简单的结果分析
- 学院1和学院3无论是拟合系数还是在截距上都比较符合预期
- 学院2似乎有点小奇怪,看上去获得特别奖励加分的人很多哦。要不然就是。。(阴谋论)
- 好吧,我们下一步就是要找出那些不太合乎常理的数值
- 找出异常值
- assert()语句 这个语句很有用,比如我们如果怀疑,这个偏差是因为漏缺数据导致的,那么可以先assert()一些确定的事情。这样就省的跑出一堆没用的数据还傻呵呵的。就像C语言一样,咋都能跑出点东西。乐死,根本不知道对不对。
-
assert(len(Data2["target"])==len(Data2["feature"])),"wrong!"
S = []
for i in range(1,all_rows2-2):
try:
sum = 0.5 * Data2["feature"][i][0]
except:
print(i)
for j in range(1,len(Data2["feature"][i])):
sum += Data2["feature"][i][j]
S.append(sum)
Q = []
for i in range(len(S)):
Q.append((S[i]-Data2["target"][i])/Data2["target"][i])
Q = [abs(i) for i in Q]
- ?结果输出
- 我们只想分析前十个数据
-
Q = [abs(i) for i in Q]
Q1 = [i for i in Q]
for i in range(10):
t = Q.index(max(Q1))
print(t,end=" ")
print(max(Q1))
Q1.remove(max(Q1))
>>>
>>>
7 0.10667617011166551
44 0.04207573632538569
70 0.03807947019867545
69 0.027375201288244812
65 0.026153846153846198
71 0.018932874354561126
58 0.017569546120058607
72 0.017543859649122806
14 0.017052375152253246
30 0.01686121919584951
- 除了线性回归,难度就没有其他的回归方法吗?
from sklearn.ensemble import RandomForestRegressor
features = Data1["feature"]
targets = Data1["target"]
randomforest = RandomForestRegressor(random_state=0)
model = randomforest.fit(features,targets)
?这个误差显然有一点点大的。。
>>>model.predict([[90,10,10,10,10],[80,20,10,10,10],[95,10,10,10,10],[90,15,5,10,10],[85,20,10,0,10],[100,10,10,10,10]])
>>>array([82.746 , 80.1668, 86.5164, 82.6754, 73.749 , 88.352 ])
好了,我们的分析将继续。
那我们能不能让随机森林干点更有用的事情呢?
比如,我们按同学的分数打等第。
from sklearn.ensemble import RandomForestClassifier
Data1["target"] = [2*(i>=90)+1*((i<90)&(i>80))+0 for i in Data1["target"]]
randomforest = RandomForestClassifier(random_state=0)
model = randomforest.fit(Data1["feature"],Data1["target"]
程序的第二行,是一个很有用的编程小技巧。值得记录
>>>model.predict([[100,20,10,10,10],[90,10,10,10,10],[80,20,10,10,10],[100,0,10,10,10]])
>>>array([2, 1, 0, 1])
嗯,效果还是不尽人意
为什么呢?
- 原因分析
- 这与我们没有做数据标准化有关,大家的德育分数都很高,在这样的情况下,如果一个人的德育成绩偏低,很可能发生错误归类。数据标准化不能完全避免这种结果,但一定程度上能削弱这种误差,但也有反例。
- 这与随机森林的原理关系很大。
- 随机森林强调分类,不注重机理,变量之间的关系并不是它考虑的
- 因此,在很多建模比赛中,线性回归往往是值得关注的。
- 全篇完
|