背景介绍
在对房价的影响因素进行模型研究之前,首先对各变量进行描述性分析,以初步判断房价的影响因素,进而建立房价预测模型
步骤如下:
(一) 因变量分析:单位面积房价分析
(二) 自变量分析:
2.1 自变量自身分布分析
2.2 自变量对因变量影响分析
(三)建立房价预测模型
3.1 线性回归模型
3.2 对因变量取对数的线性模型
3.3 考虑交互项的对数线性
(四)预测: 假设有一家三口,父母为了能让孩子在东城区上学,想买一套邻近地铁的两居室,面积是70平方米,中层楼层,那么房价大约是多少呢?
# In[1]:
"""
dist-所在区
roomnum-室的数量
halls-厅的数量
AREA-房屋面积
floor-楼层
subway-是否临近地铁
school-是否学区房
price-平米单价
"""
# In[1]:
import pandas as pd
import numpy as np
import math
import matplotlib.pyplot as plt
import matplotlib
import seaborn as sns
import statsmodels.api as sm
from numpy import corrcoef,array
#from IPython.display import HTML, display
from statsmodels.formula.api import ols
import os
os.chdir(r"D:\pydata")
# # 1 描述
# In[17]:
datall=pd.read_csv("sndHsPr.csv") #读入清洗过后的数据
print("%d",datall.shape[0]) #样本量
#%%
#%%
dat0=datall
dat0.describe(include="all").T #查看数据基本描述
# In[18]:
dat0.price=dat0.price/10000 #价格单位转换成万元
# In[19]:
#将城区的水平由拼音改成中文,以便作图输出美观
dict1 = {
u'chaoyang' : "朝阳",
u'dongcheng' : "东城",
u'fengtai' : "丰台",
u'haidian' : "海淀",
u'shijingshan' : "石景山",
u'xicheng': "西城"
}
#%%
dat0.dist = dat0.dist.apply(lambda x : dict1[x])
dat0.head()
# 1.1 因变量
#
# price
# In[20]:
matplotlib.rcParams['axes.unicode_minus']=False#解决保存图像时负号'-'显示为方块的问题
plt.rcParams['font.sans-serif'] = ['SimHei']#指定默认字体
#因变量直方图
dat0.price.hist(bins=20)
#dat0.price.plot(kind="hist",color='lightblue')
plt.xlabel("单位面积房价(万元/平方米)")
plt.ylabel("频数")
# In[21]:
print(dat0.price.agg(['mean','median','std'])) #查看price的均值、中位数和标准差等更多信息
print(dat0.price.quantile([0.25,0.5,0.75]))
# In[22]:
#查看房价最高和最低的两条观测
pd.concat([(dat0[dat0.price==min(dat0.price)]),(dat0[dat0.price==max(dat0.price)])])
# 1.2 自变量:
#
# dist+roomnum+halls+floor+subway+school+AREA
# In[23]:
#整体来看 ,第列是连续变量,不用 value_counts,其实还可以把连续和分类变量分别放到集合里
for i in range(7):
if i != 3:
print(dat0.columns.values[i],":")
print(dat0[dat0.columns.values[i]].agg(['value_counts']).T)
print("=======================================================================")
else:
continue
print('AREA:')
print(dat0.AREA.agg(['min','mean','median','max','std']).T)
# 1.2.1 dist
# In[24]:
#频次统计
dat0.dist.value_counts().plot(kind = 'pie') #绘制柱柱形图
dat0.dist.agg(['value_counts'])
#dat0.dist.value_counts()
# In[25]:
dat0.price.groupby(dat0.dist).mean().sort_values(ascending= True).plot(kind = 'barh') #不同城区的单位房价面积均值情况
#%%
dat1=dat0[['dist','price']]
dat1.dist=dat1.dist.astype("category")
dat1.dist.cat.set_categories(["石景山","丰台","朝阳","海淀","东城","西城"],inplace=True)
#dat1.sort_values(by=['dist'],inplace=True)
sns.boxplot(x='dist',y='price',data=dat1)
#dat1.boxplot(by='dist',patch_artist=True)
plt.ylabel("单位面积房价(万元/平方米)")
plt.xlabel("城区")
plt.title("城区对房价的分组箱线图")
# In[26]:
# 1.2.2 roomnum
# In[27]:
#不同卧室数的单位面积房价差异不大
dat4=dat0[['roomnum','price']]
dat4.price.groupby(dat4.roomnum).mean().plot(kind='bar')
dat4.boxplot(by='roomnum',patch_artist=True)
# 1.2.3 halls
# In[28]:
#厅数对单位面积房价有轻微影响
dat5=dat0[['halls','price']]
dat5.price.groupby(dat5.halls).mean().plot(kind='bar')
dat5.boxplot(by='halls',patch_artist=True)
# 1.2.4 floor
# In[31]:
#不同楼层的单位面积房价差异不明显
dat6=dat0[['floor','price']]
dat6.floor=dat6.floor.astype("category")
dat6.floor.cat.set_categories(["low","middle","high"],inplace=True)
dat6.sort_values(by=['floor'],inplace=True)
dat6.boxplot(by='floor',patch_artist=True)
#dat6.price.groupby(dat6.floor).mean().plot(kind='bar')
# 1.2.5 subway+school
# In[32]: 两个分类变量
print(pd.crosstab(dat0.subway,dat0.school))
sub_sch=pd.crosstab(dat0.subway,dat0.school)
sub_sch = sub_sch.div(sub_sch.sum(1),axis = 0)
sub_sch
# In[33]:
def stack2dim(raw, i, j, rotation = 0, location = 'upper left'):
'''
此函数是为了画两个维度标准化的堆积柱状图
要求是目标变量j是二分类的
raw为pandas的DataFrame数据框
i、j为两个分类变量的变量名称,要求带引号,比如"school"
rotation:水平标签旋转角度,默认水平方向,如标签过长,可设置一定角度,比如设置rotation = 40
location:分类标签的位置,如果被主体图形挡住,可更改为'upper left'
'''
import math
data_raw = pd.crosstab(raw[i], raw[j])
data = data_raw.div(data_raw.sum(1), axis=0) # 交叉表转换成比率,为得到标准化堆积柱状图
# 计算x坐标,及bar宽度
createVar = locals()
x = [0] #每个bar的中心x轴坐标
width = [] #bar的宽度
k = 0
for n in range(len(data)):
# 根据频数计算每一列bar的宽度
createVar['width' + str(n)] = dat