首页 > 编程语言 >python课程设计——爬取厦门二手房信息

python课程设计——爬取厦门二手房信息

时间:2022-12-24 12:55:44浏览次数:52  
标签:课程设计 mylist temp title python 爬取 word data opts

一 选题背景
本次项目选择了中国的厦门,通过了解厦门市二手房的情况,可以帮助人们在购房、出租等方面做出更明智的决策。可以帮助人们了解上海市经济的发展趋势。随着互联网的发展,越来越多的房地产信息通过网络发布,使用爬虫技术可以方便地收集和分析这些信息。而本次项目选择的数据来源是链家。链家是一家著名的房地产经纪公司,在厦门有着广泛的房地产业务。通过爬取厦门链家发布的二手房信息,可以获得丰富的数据,为分析提供参考。
2.
在现今毒外地务工人员洪流的影响下,拥有众多客户的链家网无疑是非常具有发展前景的,链家网顾客有许多的受众群体,普遍具有租房意向以及需求,这就代表着有许多的购买力能够产生较为不错的经济价值,在抓住了这些顾客的需求数据,能够发现更多顾客对于二手房源的具体需求进行分析,知晓二手房市场动态。
二 数据源的获取
厦门二手房信息爬虫
网址:https://xm.lianjia.com/ershoufang/

三 程序的实现

1、数据爬取与采集

data_list = [] #定义一个空的字典,用来储存爬取到的文本
for page in range(page_range):
    pgurl = url+'/pg'+str(page+1)
    print ("正在爬取的网页地址为:",pgurl)
    header = {
        'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3626.109 Safari/537.36'}
    page = requests.get(pgurl, headers=header)  #访问网址获取该 html内容
    a = page.text
    soup = BeautifulSoup(a,"lxml")  #解析该html
    for b in soup.find_all('div',class_='info clear'): #find_all 找到 div class='info clear' 的标签
        temp = []
        for wz in b.find_all('div',class_= ['title','positionInfo','tag','houseInfo','priceInfo','followInfo']):
            temp.append(wz.get_text())

 

 

2、数据清洗和处理

tag = regnum(temp[2])
#截取了二手房在链家网上的发布时间以及关注人数
date = regnum(temp[3])
#有的二手房发布时间在1年以上,未用数字说明,此处说明其发布时间
date = addnone(date,2,'>365')
#截取总价和单价
price = regnum(temp[5])
temp.extend(price)#extend() 函数用于在列表末尾一次性追加另一个序列中的多个值(用新列表扩展原来的列表)
temp.extend(date)
temp.extend(tag)
#将二手房中未给出的数字描述统一赋值为0
temp = addnone(temp,15,'0')

data_list.append(temp)

def removenone(mylist):#移除参数中空值的函数
    while '' in mylist:
        mylist.remove('')
    return mylist
def addnone(mylist,length,cha):#对文本进行标准化,使其文本格式都一样
    while len(mylist) < length:
        mylist.append(cha)
    return mylist
def regnum(s):#提取爬取到的字符串中的数值
    mylist = re.findall(r'[\d+\.\d]*', s)
    mylist = removenone(mylist)
    return mylist

效果:

 

1、文本分析,jieba分词和Wordcloud词云图

import jieba
txt = open('房源信息.txt',encoding='utf-8').read()
print(txt)
#使用精确模式进行分词
count  = jieba.lcut(txt)
#定义空字典,对分词结果进行词频统计
remove_words = [u'的', u',',u'和', u'是', u'随着', u'对于', u'对',u'等',u'能',u'都',u'。',u' ',u' ',u'中',u'在',u'了',
                 u'通常',u'如果',u',',u'\n'] # 自定义去除词库
word_count={}
for word in count:
    if word not in remove_words:
        word_count[word] = word_count.get(word, 0) + 1
#按词频对分词进行排序
items = list(word_count.items())
items.sort(key=lambda x: x[1], reverse=True)
print(items)
# print(data1)

wordcloud_1=(                                                    #实例化对象
    WordCloud(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                  #设置图表主题
    .add(
         series_name="",                                         #设置图例名称,并没什么用
         data_pair=items,                                         #设置数据
         word_size_range=[10,100],                               #字体大小范围
         shape=SymbolType.ROUND_RECT)                            #样式
    .set_global_opts(
        title_opts=opts.TitleOpts(title="词云图",                  #设置图表标题
                                  # title_textstyle_opts=opts.TextStyleOpts(font_size=10) #设置标题的字体大小
                                  ),
        tooltip_opts=opts.TooltipOpts(is_show=True),
    )
).render('房源词云图.html')

效果:

 

 

 

 

四  数据分析可视化

1.排名前十的地区平均房价折线图

line_1=(
    #实例化图表
    Line(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                          #设置图表主题
    .add_xaxis(data5['Position'].tolist())                               #设置横坐标
    .add_yaxis("总价",data5['总价'].tolist(),
               markpoint_opts=opts.MarkPointOpts(data=[opts.MarkPointItem(type_="max")]))                    #设置纵坐标1、突出显示最大值或者最小值

    .set_global_opts(                                                #全局配置
        title_opts=opts.TitleOpts(title="排名前十的地区平均房价折线图")                      #图表标题
    )
).render('排名前十的地区平均房价折线图.html')

效果:

2.排名前十的地区房源数量折线图

 

line_2=(
    #实例化图表
    Line(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                          #设置图表主题
    .add_xaxis(data1['Position'].tolist())                               #设置横坐标
    .add_yaxis("数量",data1['Title'].tolist(),
               markpoint_opts=opts.MarkPointOpts(data=[opts.MarkPointItem(type_="max")]))                    #设置纵坐标1、突出显示最大值或者最小值

    .set_global_opts(                                                #全局配置
        title_opts=opts.TitleOpts(title="排名前十的地区房源数量折线图")                      #图表标题
    )
).render('排名前十的地区房源数量折线图.html')

 

 

 

效果:

3.最受欢迎户型分布

bar = (
    Bar()
    .add_xaxis(data2['几室'].tolist())
    .add_yaxis("几室",data2['Title'].tolist())
    .add_yaxis("几厅",data3['Title'].tolist())
    .set_global_opts(title_opts=opts.TitleOpts(title="最受欢迎户型分布", subtitle="副标题"),
                    toolbox_opts=opts.BrushOpts(),)
)
bar.render('最受欢迎户型分布.html')

效果:

 

4.不同建造年份待售房占比
pie.set_global_opts(
#标题配置项
   title_opts=opts.TitleOpts(title="不同建造年份待售房占比",pos_left='70%'),
   #  图例配置项
     legend_opts=opts.LegendOpts(
     type_="scroll"
     , pos_top="20%"
     , pos_left="80%"
     , orient="vertical"
     ),
)
pie.render('不同建造年份待售房占比.html')

效果:

 

5、一元线性回归预测房价

from sklearn.linear_model import LinearRegression

model = LinearRegression()
x = data['面积'].values.reshape(-1, 1)#reshape(-1,1)转换成1列
y = data['总价']
model.fit(x, y)
print((model.predict([[600]])).round(2))#预测600平总价
import matplotlib.pyplot as plt
plt.scatter(data['面积'], y, color='blue')
plt.plot(x, model.predict(x), 'r-')
plt.grid(True)
plt.show()

效果:

 

 四 总结

  通过这次的的爬虫实验分析,得到了一个厦门二手房源的信息,这对于即将毕业的我来说还是非常有用的让我在找房源的时候有了一个较为初步的判断信息,避免了不必要的麻烦,在选择上也有着较为详细的房源选择,不仅可以根据排名来选择而且还可以根据欢迎程度选择自己想要的房源。

  在这次爬虫实验中,虽然在刚开始的时候真的是无从下手不知道该做什么方向的课题,不过好在从各种的资料中确定了方向,这次的课程设计不仅锻炼了我的整体构架思维,还提升了解决问题的能力,受益良多。

整体代码

1.爬取数据

import re
import requests
from bs4 import BeautifulSoup
import pandas as pd
def removenone(mylist):#移除参数中空值的函数
    while '' in mylist:
        mylist.remove('')
    return mylist
def addnone(mylist,length,cha):#对文本进行标准化,使其文本格式都一样
    while len(mylist) < length:
        mylist.append(cha)
    return mylist
def regnum(s):#提取爬取到的字符串中的数值
    mylist = re.findall(r'[\d+\.\d]*', s)
    mylist = removenone(mylist)
    return mylist
def lianjia(url,page_range,district):
    #Initialization
    colum_name=['Title','Position','Tag','followInfo','VR','Info',
                '总价','单价RMB/万','单价(后三位)','关注人数',
                '发布时间','几室','几厅','面积','楼层','年份']    #定义爬取到的文本的表头
    data_list = [] #定义一个空的字典,用来储存爬取到的文本
    for page in range(page_range):
        pgurl = url+'/pg'+str(page+1)
        print ("正在爬取的网页地址为:",pgurl)
        header = {
            'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3626.109 Safari/537.36'}
        page = requests.get(pgurl, headers=header)  #访问网址获取该 html内容
        a = page.text
        soup = BeautifulSoup(a,"lxml")  #解析该html
        for b in soup.find_all('div',class_='info clear'): #find_all 找到 div class='info clear' 的标签
            temp = []
            for wz in b.find_all('div',class_= ['title','positionInfo','tag','houseInfo','priceInfo','followInfo']):
                temp.append(wz.get_text())
                #截取二手房中的房间数,面积,楼层,建造时间
            tag = regnum(temp[2])
            #截取了二手房在链家网上的发布时间以及关注人数
            date = regnum(temp[3])
            #有的二手房发布时间在1年以上,未用数字说明,此处说明其发布时间
            date = addnone(date,2,'>365')
            #截取总价和单价
            price = regnum(temp[5])
            temp.extend(price)#extend() 函数用于在列表末尾一次性追加另一个序列中的多个值(用新列表扩展原来的列表)
            temp.extend(date)
            temp.extend(tag)
            #将二手房中未给出的数字描述统一赋值为0
            temp = addnone(temp,15,'0')

            data_list.append(temp)
    print("爬取完成")
    # print(data_list)
    data = pd.DataFrame(data_list,columns=colum_name)#将data转换为dataframe类型
    data.to_csv(district+'.csv')    #保存数据到CSV文件
    return data
if __name__ == '__main__':
    district_list = [(input('请输入保存文件英文名:'))] #输入
    for district in district_list:
        url = "https://xm.lianjia.com/ershoufang/"
        page_range = int(input('请输入爬取页数:'))        #输入获得翻页数量
        my = lianjia(url,page_range,district)

 

 2.可视化

import pandas as pd
import numpy as np
from pyecharts.charts import Bar,Pie,WordCloud,Line #导入图表类型
from pyecharts import options as opts #导入相关属性包
from pyecharts.charts import Page,Grid #导入页面编排包
from pyecharts.globals import ThemeType #导入主题包
from pyecharts.globals import SymbolType #词云图样式
from pyecharts.globals import ChartType
data=pd.read_csv('xiamen.csv',encoding='utf-8')
data.fillna(value=0,inplace=True)
data['Position']=data['Position'].str.replace(' ','')
data['Position']=data['Position'].str.split('-',expand=True)[1]
data1=data.groupby(by=['Position'])['Title'].count().reset_index().sort_values(['Title'])[-5:]#排名前十的区域房源数量
data2=data.groupby(by=['几室'])['Title'].count().reset_index().sort_values(['Title'])[-5:]
data3=data.groupby(by=['几厅'])['Title'].count().reset_index().sort_values(['Title'])[-5:]
data2['几室']=data2['几室'].astype('str')+'室'+data3['几厅'].astype('str')+'厅'
data4=data.groupby(by=['年份'])['Title'].count().reset_index().round(0)
data5=data.groupby(by=['Position'])['总价'].mean().reset_index().sort_values(['总价'])[-10:].round(0)
data6=data['Title'].tolist()
print(data6)
line_1=(
    #实例化图表
    Line(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                          #设置图表主题
    .add_xaxis(data5['Position'].tolist())                               #设置横坐标
    .add_yaxis("总价",data5['总价'].tolist(),
               markpoint_opts=opts.MarkPointOpts(data=[opts.MarkPointItem(type_="max")]))                    #设置纵坐标1、突出显示最大值或者最小值

    .set_global_opts(                                                #全局配置
        title_opts=opts.TitleOpts(title="排名前十的地区平均房价折线图")                      #图表标题
    )
).render('排名前十的地区平均房价折线图.html')
line_2=(
    #实例化图表
    Line(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                          #设置图表主题
    .add_xaxis(data1['Position'].tolist())                               #设置横坐标
    .add_yaxis("数量",data1['Title'].tolist(),
               markpoint_opts=opts.MarkPointOpts(data=[opts.MarkPointItem(type_="max")]))                    #设置纵坐标1、突出显示最大值或者最小值

    .set_global_opts(                                                #全局配置
        title_opts=opts.TitleOpts(title="排名前十的地区房源数量折线图")                      #图表标题
    )
).render('排名前十的地区房源数量折线图.html')

bar = (
    Bar()
    .add_xaxis(data2['几室'].tolist())
    .add_yaxis("几室",data2['Title'].tolist())
    .add_yaxis("几厅",data3['Title'].tolist())
    .set_global_opts(title_opts=opts.TitleOpts(title="最受欢迎户型分布", subtitle="副标题"),
                    toolbox_opts=opts.BrushOpts(),)
)
bar.render('最受欢迎户型分布.html')

pie=Pie()
pie.add("",[list(z) for z in zip(data4['年份'].tolist(),data4['Title'].tolist())]
      #数据标签展示
        ,label_opts=opts.LabelOpts(
            position="outside",
            formatter="{d}%"))
#  设置其他配置项
pie.set_global_opts(
#标题配置项
   title_opts=opts.TitleOpts(title="不同建造年份待售房占比",pos_left='70%'),
   #  图例配置项
     legend_opts=opts.LegendOpts(
     type_="scroll"
     , pos_top="20%"
     , pos_left="80%"
     , orient="vertical"
     ),
)
pie.render('不同建造年份待售房占比.html')

#一元回归预测
from sklearn.linear_model import LinearRegression

model = LinearRegression()
x = data['面积'].values.reshape(-1, 1)#reshape(-1,1)转换成1列
y = data['总价']
model.fit(x, y)
print((model.predict([[600]])).round(2))#预测600平总价
import matplotlib.pyplot as plt
plt.scatter(data['面积'], y, color='blue')
plt.plot(x, model.predict(x), 'r-')
plt.grid(True)
plt.show()


str="\n"
f=open('房源信息.txt','w',encoding='utf-8')
f.write(str.join(data6))
f.close()

import jieba
txt = open('房源信息.txt',encoding='utf-8').read()
print(txt)
#使用精确模式进行分词
count  = jieba.lcut(txt)
#定义空字典,对分词结果进行词频统计
remove_words = [u'的', u',',u'和', u'是', u'随着', u'对于', u'对',u'等',u'能',u'都',u'。',u' ',u' ',u'中',u'在',u'了',
                 u'通常',u'如果',u',',u'\n'] # 自定义去除词库
word_count={}
for word in count:
    if word not in remove_words:
        word_count[word] = word_count.get(word, 0) + 1
#按词频对分词进行排序
items = list(word_count.items())
items.sort(key=lambda x: x[1], reverse=True)
print(items)
# print(data1)

wordcloud_1=(                                                    #实例化对象
    WordCloud(init_opts=opts.InitOpts(theme=ThemeType.WESTEROS))                                                  #设置图表主题
    .add(
         series_name="",                                         #设置图例名称,并没什么用
         data_pair=items,                                         #设置数据
         word_size_range=[10,100],                               #字体大小范围
         shape=SymbolType.ROUND_RECT)                            #样式
    .set_global_opts(
        title_opts=opts.TitleOpts(title="词云图",                  #设置图表标题
                                  # title_textstyle_opts=opts.TextStyleOpts(font_size=10) #设置标题的字体大小
                                  ),
        tooltip_opts=opts.TooltipOpts(is_show=True),
    )
).render('房源词云图.html')

 

 

 

 

标签:课程设计,mylist,temp,title,python,爬取,word,data,opts
From: https://www.cnblogs.com/songjian49/p/17002765.html

相关文章

  • Python__12--列表元素的增、删、改、排序
    1列表元素的增、删、改、排序除sorted(),id均不变1.1加append()在列表的末尾添加一个元素测试代码:lst=[10,20,30]print(id(lst))lst.append(100)print(lst,id(l......
  • 简单介绍python中读取txt文件时split()函数的妙用
    这篇文章主要介绍了python中读取txt文件时split()函数的妙用,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教不知道大家有没有过需要从txt文......
  • python使用request发送x-www-form-urlencoded类型的数据
    场景:当接口的Content-Type类型是x-www-form-urlencoded,使用json类型去请求,无法请求成功解决方法:使用parse.urlencode()方法对json数据进行解码处理,再传入。实例代码如下......
  • Python学习笔记--从继承开始继续
    继承的基础语法单继承:多继承:一个子类继承多个父类pass关键字补全语法注意事项:复写和使用父类成员复写父类成员也就是相当于Java中的方法重写调用父类成员......
  • Python学习笔记--第二阶段啦
    初识对象示例:类的成员方法上图中的self必须填写!!!示例:类和对象有c和c++语言基础的话,就会发现其实是一样的道理,只是实现代码有差异构造方法(init)示例:注意:......
  • Python-基于flask的接口框架
    ✅作者简介:热爱科研的算法开发者,Python、Matlab项目可交流、沟通、学习。......
  • python标准化日期转换
    将.号\号-号的日期格式,全部统一成一种方式#coding:utf-8importre#目标:2021-05-28content="""白日依2021/05/26山尽,黄河入2021.05.27海流。欲穷05-28-2020千里......
  • Python爬虫——上海市链家二手房数据爬取及可视化分析
    一、选题的背景本次项目选择了中国的一线城市——上海市,通过了解上海市二手房的情况,可以帮助人们在购房、出租等方面做出更明智的决策。可以帮助人们了解上海市经济的......
  • 树莓派 python 直接控制sg90舵机
     必须是sg90s金属齿轮的 塑料sg90不知道为什么不行 importRPi.GPIOasGPIOimporttimeservoPIN=17#GPIO口GPIO.setmode(GPIO.BCM)GPIO.setup(servoPIN,......
  • Python网络爬虫—对京东口红销售的数据分析
    一、选题的背景 对电商来说,抓取某些数据,再进行分析,可以有效地反映出数据在某个区间内变化情况。数据受某些因素而发生巨大的影响,也可以借助分析的数据来规划相关项目的后......