波士顿房价预测2(多元线性回归)

2019-03-05  本文已影响0人  Acapella_Zhang

模型思想

多元线性回归(multiple linear regression) 模型的目的是构建一个回归方程,利用多个自变量估计因变量,从而解释和预测因变量的值。多元线性回归模型中的因变量和大多数自变量为定量值,某些定性指标需要转换为定量值才能应用到回归方程中。

意义

事物的联系也是多方面的,而影响事物发展的因素是多样的。由多个自变量的最优组合共同来估计因变量,比单一的自变量预测更有效,更符合实际。
比如糖尿病人的血糖变化可能受胰岛素、糖化血红蛋白、血清总胆固醇、甘油三酯等多种指标的影响。但很多情况下,由于自变量的单位是不一样的,需要做标准化处理。比如在消费水平预测模型中,工资水平、受教育程度、职业、地区、家庭负担等因素都会影响到消费水平,而这些影响因素的单位和量级肯定是不同的,虽然不会影响自变量的重要程度,但是对回归系数的大小还是有直接影响作用的。标准化回归系数没有单位,其值越大,说明该自变量对因变量的影响越大。

https://www.jianshu.com/p/2ce27e88d78c

1.加载数据集并试着分析特征

from sklearn.datasets import load_boston
boston = load_boston()
print(boston.DESCR)

Boston House Prices dataset
===========================
Notes


Data Set Characteristics:
:Number of Instances: 506
:Number of Attributes: 13 numeric/categorical predictive
:Median Value (attribute 14) is usually the target
:Attribute Information (in order):

  • CRIM per capita crime rate by town
  • ZN proportion of residential land zoned for lots over 25,000 sq.ft.
  • INDUS proportion of non-retail business acres per town
  • CHAS Charles River dummy variable (= 1 if tract bounds river; 0 otherwise)
  • NOX nitric oxides concentration (parts per 10 million)
  • RM average number of rooms per dwelling
  • AGE proportion of owner-occupied units built prior to 1940
  • DIS weighted distances to five Boston employment centres
  • RAD index of accessibility to radial highways
  • TAX full-value property-tax rate per $10,000
  • PTRATIO pupil-teacher ratio by town
  • B 1000(Bk - 0.63)^2 where Bk is the proportion of blacks by town
  • LSTAT % lower status of the population
  • MEDV Median value of owner-occupied homes in $1000's


查看数据集的关键字

boston.keys()
#dict_keys(['data', 'target', 'feature_names', 'DESCR'])

1.2 将数据集转化为dataframe

bostonDf_X = pd.DataFrame(boston.data,columns=boston.feature_names)
bostonDf_y = pd.DataFrame(boston.target,columns=['houseprice'])#注意加列名称

#合并dataframe
bostonDf = pd.concat([bostonDf_X,bostonDf_y],axis=1)#axis=1为横向操作
bostonDf.shape#(506, 14)
bostonDf.head() #看一下数据集

然后对整体数据进行大致分析

print("最大值:",np.max(boston.target))
print("最小值:",np.min(boston.target))
print("平均值:",np.mean(boston.target))
bostonDf.describe()

最大值: 50.0
最小值: 5.0
平均值: 22.532806324110677

然后对其中一些字段进行特征分析

1.2.1 CRIM分析

plt.scatter(df['CRIM'], y)
plt.title('城镇人均犯罪率与房价散点图')
plt.xlabel('城镇人均犯罪率')
plt.ylabel('房价')
plt.show()

1.2.2 RM分析

先对要重复出现的代码进行封装

def drawScatter(x, y, xlabel):
    plt.scatter(x, y)
    plt.title('%s与房价散点图' %xlabel)
    plt.xlabel(xlabel)
    plt.ylabel('房价')
    plt.yticks(range(0,60,5))
    plt.grid()
    plt.show()

同样的可以画出其他因素与房价之间关系的散点图


1.3对数据进行正规化处理

使用sklearn中的StandardScaler进行处理

#进行数据预处理
from sklearn.preprocessing import StandardScaler
scaler = StandardScaler()
#将数据归化到正态分布,均值为0,方差为1
bostonStd_1 = scaler.fit_transform(bostonDf.values)
showbostonStd_1 = pd.DataFrame(bostonStd_1,columns=bostonDf.columns)
showbostonStd_1.head(10)

1.4 对数据集进行切分

x_train,x_test,y_train,y_test = train_test_split(bostonStd_1[:,[0,13]],bostonStd_1[:,[13]],test_size=0.3,random_state=0)

1.5建立模型进行预测

#进行建模
from sklearn.linear_model import LinearRegression
regr = LinearRegression()
regr.fit(x_train,y_train)

y_pred = regr.predict(x_test)
regr.score(x_test,y_test)

此时得到的score为1.0,可能过拟合,之后将使用网格调参进行优化处理

regr.coef_ #看一下此时的权重
array([[-1.19858618e-01,  4.44233009e-02,  1.18612465e-02,
         2.51295058e+00, -1.62710374e+01,  3.84909910e+00,
        -9.85471557e-03, -1.50002715e+00,  2.41507916e-01,
        -1.10671867e-02, -1.01897720e+00,  6.95273216e-03,
        -4.88110587e-01]])

由此可以得知第七个因素对房价负增长的影响最大(1940年以前建成的业主自住单位的占比),而第12个因素对房价的增长影响最大(黑人比例!?)

1.6计算评价指标

#根据公式计算结果
mse_test = np.sum((y_pred-y_test)**2)/len(y_test)
mae_test = np.sum(np.absolute(y_pred-y_test))/len(y_test)
rmse_test = mse_test**0.5
r2_score = 1-(mse_test/np.var(y_test))
print("r2_score为:",r2_score)
print("mae为:",mae_test)
print("mse为:",mse_test)
print("rmse为:",rmse_test)

r2_score为: 1.0
mae为: 4.269359902158972e-16
mse为: 3.4968787098127684e-31
rmse为: 5.913441223021303e-16

2.使用网格搜索进行调参

网格搜索是一种调参手段;穷举搜索:在所有候选的参数选择中,通过循环遍历,尝试每一种可能性,表现最好的参数就是最终的结果。其原理就像是在数组里找最大值。(为什么叫网格搜索?以有两个参数的模型为例,参数a有3种可能,参数b有4种可能,把所有可能性列出来,可以表示成一个3*4的表格,其中每个cell就是一个网格,循环过程就像是在每个网格里遍历、搜索,所以叫grid search)
通过调用sklearn中的grid_search.GridSearchCV来完成

#k近邻网络搜索来进行调参
from sklearn.grid_search import GridSearchCV
from sklearn.neighbors import KNeighborsRegressor

knn_reg = KNeighborsRegressor()
grid_param = [
    {
        'weights':['uniform'],
        'n_neighbors':[i for i in range(1,11)]
    },
    {
        'weights':['distance'],
        'n_neighbors':[i for i in range(1,11)],
         'p':[i for i in range(1,6)]
    }
]
knn_reg = KNeighborsRegressor()
grid_search = GridSearchCV(knn_reg,grid_param,n_jobs=-1,verbose=2,cv=10)
# 调用fit方法执行网格搜索
grid_search.fit(x_train,y_train.astype('int'))

print(grid_search.best_params_)
print(grid_search.best_score_)
print(grid_search.best_estimator_.score(x_test,y_test))

得到

{'n_neighbors': 3, 'p': 1, 'weights': 'distance'}
0.9397867256628897
#在测试集上的最高分数
0.7577379984560788
上一篇下一篇

猜你喜欢

热点阅读