用Python实现全国二手房数据抓取+地图展示

最近各种政策的出台,导致二手房的价格波动巨大,本文二哥来带领大家通过链家二手房为例,简单分析一下全国多个地区的二手房价格。

【建议先点赞、再收藏】

一、思路❤️

想要获取链家全国二手房的信息,首先我们进入到相关的二手房页面观察一下(以北京为例):
在这里插入图片描述
这里可以看到,我们能够看到北京的二手房信息,但是并没有其他省份和城市的选项,因此回到首页寻找各大城市的选项,通过点击首页左上角的城市按钮,可以进入到相关的省份-城市页面:
在这里插入图片描述
有了省份-城市页面之后,我们就可以通过该页面获取各个城市的url信息,然后再访问各个url进行二手房数据的抓取就可以了。
整体流程如下
在这里插入图片描述

二、获取城市信息❤️

获取城市信息时,我们直接获取到城市页面的HTML进行解析即可,这里因为HTML中有些省份信息的构造不同,因此解析出大部分省份信息使用。
获取城市信息的代码如下:

import random
import time
import csv
import requests
from lxml import etree
import pandas as pd

# 获取各个省份,城市的信息
def city(i, j):
    try:
        p1 = "//li[@class='city_list_li city_list_li_selected'][{}]/div[@class='city_list']/div[@class='city_province']/div[@class='city_list_tit c_b']/text()".format(
            i)
        province = et.xpath(p1)[0]
        cn1 = "//li[@class='city_list_li city_list_li_selected'][{}]/div[@class='city_list']/div[@class='city_province']/ul/li[{}]/a/text()".format(
            i, j)
        city_name = et.xpath(cn1)[0]
        cu1 = "//li[@class='city_list_li city_list_li_selected'][{}]/div[@class='city_list']/div[@class='city_province']/ul/li[{}]/a/@href".format(
            i, j)
        city_url = et.xpath(cu1)[0]
    except:
        return 0, 0, 0
    return province, city_name, city_url


# 生成省份-城市-URL字典
dic1 = {}
count = 1
for i in range(1, 15):
    for j in range(1, 6):
        province, city_name, city_url = city(i, j)
        if province != 0:
            dic1[count] = [province, city_name, city_url]
            count += 1
        else:
            pass
# dic1

获取后的结果样例如下:
在这里插入图片描述

三、获取二手房数据❤️

有了各个城市的主页信息之后,我们就可以尝试通过构造二手房的网址来进行多城市的数据获取了,构造二手房网址的时候我们只需要在URL后缀加上ershoufang/pg{}/即可。有了网址我们就能够按照正常的方式进行数据的获取了:

f = open('全国二手房数据.csv', 'a', encoding='gb18030')
write = csv.writer(f)


def parser_html(pr_ci, page, User_Agent):

    headers = {
        'User-Agent': User_Agent[random.randint(0,
                                                len(User_Agent) - 1)]
    }

    for i in range(1, len(pr_ci) + 1):
        province = pr_ci.get(i)[0]
        city = pr_ci.get(i)[1]
        url = pr_ci.get(i)[2] + 'ershoufang/pg{}/'.format(page)
        print(url)
        html = requests.get(url=url, headers=headers).text
        eobj = etree.HTML(html)
        li_list = eobj.xpath("//li[@class='clear LOGVIEWDATA LOGCLICKDATA']")
        for li in li_list:
            title_list = li.xpath(".//div[@class='title']/a/text()")
            title = title_list[0] if title_list else None
            name_list = li.xpath(".//div[@class='positionInfo']/a[1]/text()")
            name = name_list[0] if name_list else None
            area_list = li.xpath(".//div[@class='positionInfo']/a[2]/text()")
            area = area_list[0] if area_list else None
            info_list = li.xpath(".//div[@class='houseInfo']/text()")
            info = info_list[0] if info_list else None

            if info:
                model = size = face = decorate = floor = year = type1 = None
                info_list1 = info.split("|")
                for i in info_list1:

                    if '室' in i:
                        model = i
                    elif '平米' in i:
                        size = i
                    elif '东' in i or '西' in i or '南' in i or '北' in i:
                        face = i
                    elif '装' in i or '毛' in i:
                        decorate = i
                    elif '层' in i:
                        floor = i
                    elif '年' in i:
                        year = i
                    elif '板' in i or '塔' in i:
                        type1 = i
                    else:
                        pass

            else:
                model = size = face = decorate = floor = year = type1 = None
            follow_list = li.xpath(".//div[@class='followInfo']/text()")
            follow = follow_list[0].split(
                '/')[0].strip() if follow_list else None
            time1 = follow_list[0].split(
                '/')[1].strip() if follow_list else None
            price_list = li.xpath(".//div[@class='totalPrice']/span/text()")
            price = price_list[0] + '万' if price_list else None
            unit_list = li.xpath(".//div[@class='unitPrice']/span/text()")
            unit = unit_list[0][2:-4] if unit_list else None

            # 具体的城市+楼房信息
            list1 = [
                province, city, url, title, name, area, model, size, face,
                decorate, floor, year, type1, follow, time1, price, unit
            ]

            write.writerow(list1)
        time.sleep(random.randint(2, 5))


def serve_forever():
    write.writerow([
        'province', 'city', 'url', 'title', 'name', 'area', 'model', 'size',
        'face', 'decorate', 'floor', 'year', 'type', 'follow', 'time', 'price',
        'unit'
    ])
    try:
        for i in range(1, 3):
            parser_html(dic1, i, User_Agent)
            time.sleep(random.randint(1, 3))
    except:
        pass

进行爬取后的数据如下:
在这里插入图片描述

四、绘图❤️

既然我们进行的是对全国数据的抓取,那么最好的呈现方式当然是通过地图展示数据,这里我们通过房源数量的多少作为例子进行地图展示,对于其他的维度进行数据替换即可。
实现方式如下:

from pyecharts import options as opts
from pyecharts.charts import Geo
from pyecharts.faker import Faker
from pyecharts.globals import ChartType
import pandas as pd

ljdata = pd.read_csv("全国二手房数据.csv",encoding = 'gb18030')
pro_num = ljdata['province'].value_counts()
c = (
    Geo()
    .add_schema(maptype="china")
    .add(
        "房源数量",
        [list(z) for z in zip(pro_num.index, pro_num.values)],
        type_=ChartType.HEATMAP,
    )
    .set_series_opts(label_opts=opts.LabelOpts(is_show=False))
    .set_global_opts(
        visualmap_opts=opts.VisualMapOpts(),
        title_opts=opts.TitleOpts(title="Geo-HeatMap"),
    )
)
c.render_notebook()
c.render()

运行后的结果如下:
在这里插入图片描述
至此我们的数据获取+可视化就完成了。

❤️点赞呦!❤️
🌟收藏呦!🌟
💎关注呦!💎

  • 7
    点赞
  • 32
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 8
    评论
链家二手数据分析可以通过Python数据分析库pandas、数据可视化库matplotlib和数据获取库requests来实现。以下是一个简单的数据分析流程: 1.获取数据:通过requests库获取链家二手数据,并将数据保存为CSV文件。 ```python import requests import pandas as pd # 获取数据 url = 'https://bj.lianjia.com/ershoufang/' headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36'} r = requests.get(url, headers=headers) r.encoding = r.apparent_encoding # 将数据保存为CSV文件 df = pd.read_html(r.text)[0] df.to_csv('lianjia.csv', index=False) ``` 2.数据清洗:清洗数据,删除无用的列,处理缺失值和异常值。 ```python # 数据清洗 df = pd.read_csv('lianjia.csv') df.drop(['id', 'url', 'community', 'district'], axis=1, inplace=True) df.dropna(inplace=True) df = df[df['price'] > 0] ``` 3.数据分析:利用pandas进行数据统计分析,例如计算均价、面积占比、源数量等。 ```python # 数据统计分析 print('二手均价:{:.2f}万元'.format(df['price'].mean())) print('面积占比:\n{}'.format(df['area'].value_counts(normalize=True))) print('源数量:\n{}'.format(df['district'].value_counts())) ``` 4.数据可视化:使用matplotlib进行数据可视化,例如绘制二手均价和源数量的柱状图、绘制面积分布的饼图等。 ```python import matplotlib.pyplot as plt # 绘制二手均价和源数量的柱状图 fig, ax = plt.subplots(1, 2, figsize=(12, 4)) df.groupby('district')['price'].mean().sort_values().plot(kind='barh', ax=ax[0]) ax[0].set_xlabel('Price (10K RMB)') df['district'].value_counts().plot(kind='barh', ax=ax[1]) ax[1].set_xlabel('Count') plt.tight_layout() plt.show() # 绘制面积分布的饼图 area_count = df['area'].value_counts(normalize=True).reset_index() area_count.columns = ['Area', 'Percentage'] area_count['Percentage'] = area_count['Percentage'].apply(lambda x: round(x * 100, 2)) plt.pie(area_count['Percentage'], labels=area_count['Area']) plt.title('Area Distribution') plt.show() ``` 通过以上流程,我们可以对链家二手数据进行简单分析和可视化,获得一些有用的信息。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 8
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

二哥不像程序员

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值