背景

一般我们在进行数据分析时,如果到了收集数据的时刻。需要确定哪种数据对我们进行数据分析是有意义的,哪种数据是对我们要进行的分析是无帮助的。我们就要进行数据的相关性分析。比如分析某个特定群体寿命比较长的原因时,将子女工作所在的城市作为其中一项因子进行统计分析,显然是不大合适的。当然所举实例,逻辑可能比较明显。在实际操作过程中,可能相关的逻辑关系没有这么明显,需要通过相关性分析来确定此特征是否作为关键因素进行分析。

数据准备

爬虫是无往不利的,此博客使用链家网的天津二手房数据作为数据来源,针对面积,楼层,是否精装等信息,进行分析几种因素对单价的影响

import requests
from bs4 import BeautifulSoup
import json
import time

houseList = []
'''
    获得平米数
'''
def getArea(templateStrList):
    for templateStr in templateStrList:
        templateStr = str(templateStr.strip())
        if "平米" in templateStr:
            return templateStr.replace('平米', '')
    return 0

'''
    简装还是精装   精装 2 简装 1  其他是0
'''
def getDecorate(templateStrList):
    for templateStr in templateStrList:
        templateStr = str(templateStr.strip())
        if "精装" in templateStr:
            return 2
        if "简装" in templateStr:
            return 1
    return 0

'''
    高楼层 2 中楼层 1 低楼层 2
'''
def getFloorLevel(templateStrList):
    for templateStr in templateStrList:
        templateStr = str(templateStr.strip())
        if "高楼层" in templateStr:
            return 2
        if "中楼层" in templateStr:
            return 1
    return 0


def getLianJia(url = '', pageIndex = 0):
    response = requests.get(url)
    response_text = response.text
    struct_response = BeautifulSoup(response_text,'lxml')
    ul = struct_response.find('ul', {'class':'sellListContent'})
    lis = ul.find_all('li')
    for li in lis:
        houseStruct = {}
        priceInfo = li.find('div', {'class':'unitPrice'})
        if priceInfo:
            # 单价
            unitPrice = str(priceInfo.get_text())
            unitPrice = unitPrice.replace('单价','')
            unitPrice = unitPrice.replace('元/平米','')
            houseStruct['unitPrice'] = unitPrice
        totalPrice = li.find('div', {'class':'totalPrice'})
        if totalPrice:
            houseStruct['totalPrice'] = totalPrice.get_text()
            houseStruct['totalPrice'] = houseStruct['totalPrice'].replace('万','')

        houseIcon = li.find('div', {'class':'houseInfo'})
        if houseIcon:
            houseIconList = str(houseIcon.get_text())
            houseIconList = houseIconList.split('|')
            houseStruct['area'] = getArea(houseIconList)
            houseStruct['decorate'] = getDecorate(houseIconList)
            houseStruct['getFloorLevel'] = getFloorLevel(houseIconList)
        positionInfo = li.find('div', {'class':'positionInfo'})
        if positionInfo:
            positionInfo = str(positionInfo.get_text())
            positionInfo = positionInfo.split('-')
            houseStruct['xiaoqu'] = positionInfo[0].strip()
            houseStruct['position'] = positionInfo[1].strip()
        houseList.append(houseStruct)
        #print(houseStruct)
    pageInfo = struct_response.find('div', {'class':'page-box house-lst-page-box'})
    pageTotal = 0

    if pageInfo:
        pageInfo = pageInfo['page-data']
        pageInfo = json.loads(pageInfo)
        pageTotal = pageInfo['totalPage']
    #pageTotal = 3
    pageIndex = pageIndex + 1
    if pageIndex <= pageTotal:
        time.sleep(3)
        print('https://tj.lianjia.com/ershoufang/pg'+str(pageIndex)+'/')
        getLianJia('https://tj.lianjia.com/ershoufang/pg'+str(pageIndex)+'/', pageIndex)
    return

def writeCSV():
    # 导入CSV安装包
    import csv

    # 1. 创建文件对象
    f = open('data.csv', 'w', encoding='utf-8')

    # 2. 基于文件对象构建 csv写入对象
    csv_writer = csv.writer(f)

    # 3. 构建列表头
    csv_writer.writerow(["单价", "总价", "面积","精装", "楼层","小区", "位置"])
    for item in houseList:
        if 'unitPrice' not in item.keys():
            continue
        if 'totalPrice' not in item.keys():
            continue
        if 'area' not in item.keys():
            continue
        if 'decorate' not in item.keys():
            item['decorate'] = 0
        if 'getFloorLevel' not in item.keys():
            item['getFloorLevel'] = 0
        if 'xiaoqu' not in item.keys():
            item['xiaoqu'] = ''
        if 'position' not in item.keys():
            item['position'] = ''
        csv_writer.writerow([item['unitPrice'], item['totalPrice'], item['area'], item['decorate'],
                             item['getFloorLevel'], item['xiaoqu'], item['position']])

    # 5. 关闭文件
    f.close()


getLianJia('https://tj.lianjia.com/ershoufang/', 1)
writeCSV()

 

相关性分析的几种方式

使用散点图进行观察

def image():
    import matplotlib.pyplot as plt
    data = pd.read_csv('data.csv')
    plt.scatter(data['面积'],data['单价'])
    # 画出散点图
    plt.savefig('area.jpg')
    plt.clf()
    plt.scatter(data['楼层'], data['单价'])
    plt.savefig('floor.jpg')
    plt.clf()
    plt.scatter(data['精装'], data['单价'])

    plt.savefig('jingzhuang.jpg')

面积与单价的散点图

相关性分析实战_数据挖掘

楼层和单价的散点图

相关性分析实战_数据挖掘_02

 

精装和单价的散点图

相关性分析实战_数据挖掘_03

相关系数计算

'''
    在说明变量之间线性相bai关程度时,根据经验,按照相关系数的大小将相关程度分为以下几种情况:|rl≥0.8时,可视为两个变量之间高度相关;
    0.5≤|rl<0.8时,可视为中度相关;0.3≤|rl<0.5时,视为低度相关; |rl<0.3时,说明两个变量之间的相关程度极弱,可视为不相关。
    
    
    在实际问题中,相关系数一般都是用样本数据计算得到的,因而带有一定的随机性,尤其 是样本容量比较小时,这种随机性更大,此时,
    用样本相关系数估计总体相关系数可信度会受到很大质疑,也就是说,样本相关系数并不能说明样本来自的两个总体是否具有显著线性关系。
    因此,需要对其进行统计推断,通过检验的方法确定变量之间是否存在相关性,即要对总体相关系数ρ=0进行显著性检验。
    
    
    一、一般来说,取bai绝对值du后,0-0.09为没有相关zhi性,0.3-弱,dao0.1-0.3为弱相关,0.3-0.5为中等相关,0.5-1.0为强相关。
        但是,往往还需要做显zhuan著性差异检验,即t-test,来检验两组数据是否显著相关,这在SPSS里面会自动计算的。
    二、样本数越是大,需要达到显著性相关的相关系数就会越小。所以这关系到样本大小,如果样本很大,比如说超过300,往往分析出来的相关
        系数比较低,比如0.2,因为样本量的增大造成了差异的增大,但显著性检验却认为这是极其显著的相关。
    三、判断强弱主要看显著性,而非相关系数本身。但在撰写论文时需要同时报告这两个统计数据。
'''
def dataCorr():
    # columns=['单价', '总价','面积','精装','楼层','小区','位置']
    data = pd.read_csv('data.csv')
    print("面积和单价的相关系数"+str(data.面积.corr(data.单价)))  # -0.2202960640486464   面积越大,单价越低
    print("精装和单价的相关系数"+str(data.精装.corr(data.单价)))  #0.15484985152675848   装修越好,单价越高
    print("楼层和单价的相关系数"+ str(data.楼层.corr(data.单价))) # -0.04967947281316401   楼层越高,单价越低???
    #print(data.单价.corr(data.小区))
    #print(data.单价.corr(data.位置))

目前能看到,单价与面积的相关性还是相对最大的(绝对值越大,相关性越大)。但是我们知道,房价除了和面积,是否精装修,楼层位置,还有隶属哪个小区,是否学区,小区里的位置等等诸多因素相关。在写这篇博客时,一度曾想将小区字段量化。后来发现如果将小区量化,就需要了解小区的各个方面之后给小区打分,又是一个大工程,只能暂时搁置不表(是否可以将小区内房价的平均值计算出来,作为其分数呢???哈哈)

大家有没有注意到,以上都是探索单一因素对结果(单价)的影响。那如果是多因素相互作用最终导致最后的结果呢?我思来想去,觉得本末倒置了。相关性计算的核心诉求,就是想要探索哪几个字段是相关字段,可以作为探索分析模型的关键因素进行模型构建,目前只需要探索单一因素就好。