用Matplotlib轻松复刻分析图,看看哪个城市买房最自由


作者 | 费弗里
来源 |?Python大数据分析
简介

复刻过程「1 坐标系部分」
「2 颜色填充」

图4import?geopandas?as?gpd
from?shapely.geometry?import?LineString,?Point,?Polygon
import?matplotlib.pyplot?as?plt
import?numpy?as?np
import?warnings
plt.rcParams['font.sans-serif']?=?['SimHei']?#?解决matplotlib中文乱码问题
plt.rcParams['axes.unicode_minus']?=?False?#?解决matplotlib负号显示问题
warnings.filterwarnings('ignore')
#?设置中心点在南极点的正射投影
crs?=?'+proj=ortho?+lon_0=0?+lat_0=-90'
#?构建经度线并设置对应经纬度的地理坐标系
lng_lines?=?gpd.GeoDataFrame({
????'geometry':?[LineString([[lng,?-90],?[lng,?-78]])?for?lng?in?np.arange(10,?220,?210?/?38)]},?
????crs='EPSG:4326')
#?构建纬度线并设置为对应经纬度的地理坐标系
lat_lines?=?gpd.GeoDataFrame({
????'geometry':?[LineString([[lng,?lat]?for?lng?in?range(10,?220)])?for?lat?in?range(-90,?-79,?2)]},?
????crs='EPSG:4326')
2.2.2 绘制指标折线

def?fake_index(value):
????
????fake?=?[]
????fake.append(value+np.random.uniform(5,?10))
????fake.append(value-np.random.uniform(5,?10))
????
????return?np.random.choice(fake,?size=2,?replace=False).tolist()
data['购房自由指数'],?data['租房自由指数']?=?list(zip(*data['居住自由指数'].apply(fake_index)))
#?修正伪造数据中大于100和小于0的情况
data.loc[:,?'居住自由指数':]?=?data.loc[:,?'居住自由指数':].applymap(lambda?v:?100?if?v?>?100?else?v)
data.loc[:,?'居住自由指数':]?=?data.loc[:,?'居住自由指数':].applymap(lambda?v:?0?if?v?<?0?else?v)
data.head()


#?为每个城市生成1条经线
lng_lines?=?gpd.GeoDataFrame({
????'geometry':?[LineString([[lng,?-90],?[lng,?-78]])?for?lng?in?np.arange(10,?220,?210?/?data.shape[0])]},?
????crs='EPSG:4326')
#?居住自由指数对应的折线
line1?=?gpd.GeoDataFrame({
????'geometry':?[LineString([(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
????????????????????????????????????????????????????????????data['居住自由指数_映射值'])])]},?
????crs='EPSG:4326')
#?居住自由指数对应的折线上的散点
scatter1?=?gpd.GeoDataFrame({
????'geometry':?[Point(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
?????????????????????????????????????????????????????data['居住自由指数_映射值'])]},?crs='EPSG:4326')
#?购房自由指数对应的折线
line2?=?gpd.GeoDataFrame({
????'geometry':?[LineString([(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
????????????????????????????????????????????????????????????data['购房自由指数_映射值'])])]},?
????crs='EPSG:4326')
#?购房自由指数对应的折线上的散点
scatter2?=?gpd.GeoDataFrame({
????'geometry':?[Point(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
?????????????????????????????????????????????????????data['购房自由指数_映射值'])]},?crs='EPSG:4326')
#?租房自由指数对应的折线
line3?=?gpd.GeoDataFrame({
????'geometry':?[LineString([(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
????????????????????????????????????????????????????????????data['租房自由指数_映射值'])])]},?
????crs='EPSG:4326')
#?租房自由指数对应的折线上的散点
scatter3?=?gpd.GeoDataFrame({
????'geometry':?[Point(lng,?lat)?for?lng,?lat?in?zip(np.arange(10,?220,?210?/?data.shape[0]),
?????????????????????????????????????????????????????data['租房自由指数_映射值'])]},?crs='EPSG:4326')
?????????????????????????????
fig,?ax?=?plt.subplots(figsize=(8,?8))
#?绘制经度线与纬度线
ax?=?lng_lines.to_crs(crs).plot(ax=ax,?linewidth=0.4,?edgecolor='lightgrey')
ax?=?lat_lines.to_crs(crs).plot(ax=ax,?linewidth=0.75,?edgecolor='grey',?alpha=0.8)
ax?=?line1.to_crs(crs).plot(ax=ax,?color='black',?linewidth=1)
ax?=?scatter1.to_crs(crs).plot(ax=ax,?color='black',?markersize=12)
ax?=?line2.to_crs(crs).plot(ax=ax,?color='#00CED1',?linewidth=0.6)
ax?=?scatter2.to_crs(crs).plot(ax=ax,?color='#00CED1',?markersize=4)
ax?=?line3.to_crs(crs).plot(ax=ax,?color='lightgrey',?linewidth=0.6)
ax?=?scatter3.to_crs(crs).plot(ax=ax,?color='lightgrey',?markersize=4)
ax.axis('off');?#?关闭坐标轴
fig.savefig('图11.png',?dpi=500,?inches_bbox='tight',?inches_pad=0)




fig,?ax?=?plt.subplots(figsize=(8,?8))
#?绘制经度线与纬度线
ax?=?lng_lines.to_crs(crs).plot(ax=ax,?linewidth=0.4,?edgecolor='lightgrey')
ax?=?lat_lines.to_crs(crs).plot(ax=ax,?linewidth=0.75,?edgecolor='grey',?alpha=0.8)
ax?=?line1.to_crs(crs).plot(ax=ax,?color='black',?linewidth=1)
ax?=?scatter1.to_crs(crs).plot(ax=ax,?color='black',?markersize=12)
ax?=?line2.to_crs(crs).plot(ax=ax,?color='#00CED1',?linewidth=0.6)
ax?=?scatter2.to_crs(crs).plot(ax=ax,?color='#00CED1',?markersize=4)
ax?=?line3.to_crs(crs).plot(ax=ax,?color='lightgrey',?linewidth=0.6)
ax?=?scatter3.to_crs(crs).plot(ax=ax,?color='lightgrey',?markersize=4)
ax?=?polygon1.difference(polygon2).plot(ax=ax,?color='#00CED1',?alpha=0.2)
polygon2.difference(polygon1).plot(ax=ax,?color='lightgrey',?alpha=0.6)
ax.axis('off');?#?关闭坐标轴
fig.savefig('图13.png',?dpi=500,?inches_bbox='tight',?inches_pad=0)




更多精彩推荐
关注公众号:拾黑(shiheibook)了解更多
[广告]赞助链接:
四季很好,只要有你,文娱排行榜:https://www.yaopaiming.com/
让资讯触达的更精准有趣:https://www.0xu.cn/
关注网络尖刀微信公众号随时掌握互联网精彩
赞助链接
排名
热点
搜索指数
- 1 习近平将发表二〇二六年新年贺词 7904141
- 2 2026年国补政策来了 7808738
- 3 东部战区:开火!开火!全部命中! 7712893
- 4 2026年这些民生政策将惠及百姓 7616985
- 5 小学食堂米线过期2.5小时被罚5万 7519709
- 6 解放军喊话驱离台军 原声曝光 7428214
- 7 为博流量直播踩烈士陵墓?绝不姑息 7327605
- 8 每月最高800元!多地发放养老消费券 7238391
- 9 数字人民币升级 1月1日起将计付利息 7141831
- 10 2026年1月1日起 一批新规将施行 7040675








AI100
