關(guān)于Python可視化Dash工具—Choropleth_Mapbox地圖實現(xiàn)
本文轉(zhuǎn)載自微信公眾號「python與大數(shù)據(jù)分析」,作者一只小小鳥鳥。轉(zhuǎn)載本文請聯(lián)系python與大數(shù)據(jù)分析公眾號。
有兩周沒更新公眾號,一來是工作有點忙,二來是被地圖的事情攪和的不行了,事情沒搞清楚前寫文檔是對自己最大的不尊重,關(guān)于choropleth_mapbox地圖實現(xiàn),有很多坑在里面。主要的因素是對geojson不夠了解,以及choropleth_mapbox對參數(shù)的解釋一直是言之不詳。
GeoJSON是一種對各種地理數(shù)據(jù)結(jié)構(gòu)進(jìn)行編碼的格式,GeoJSON是用json的語法表達(dá)和存儲地理數(shù)據(jù),可以說是json的子集。GeoJSON對象可以表示幾何、特征或者特征集合。GeoJSON支持下面幾何類型:點、線、面、多點、多線、多面和幾何集合。GeoJSON里的特征包含一個幾何對象和其他屬性,特征集合表示一系列特征。
GeoJSON總是由一個單獨的對象組成。這個對象表示幾何、特征或者特征集合。
GeoJSON對象可能有任何數(shù)目成員。
GeoJSON對象必須有一個名字為"type"的成員。這個成員的值是由GeoJSON對象的類型所確定的字符串。
type成員的值必須是下面之一:"Point", "MultiPoint", "LineString", "MultiLineString", "Polygon", "MultiPolygon", "GeometryCollection", "Feature", 或者 "FeatureCollection"。
以下是個geojosn的樣例
{
"type": "FeatureCollection",
"features": [
{"type":"Feature",
"properties":{},
"geometry":{
"type":"Point",
"coordinates":[105.380859375,31.57853542647338]
}
}
]
}
關(guān)于全球地圖、中國地圖、省域地圖的geojson文件均可以下載到,但格式略有區(qū)別,比如全球地圖有id即國家簡寫,在properties下的name中也有全稱。
但中國地圖有adcode,name、級別、中心點等等屬性。
在實現(xiàn)choropleth_mapbox的過程中,地圖一直無法正常顯示,原因有二,其一plotly基于d3.js,geojson文件的加載比較耗時,而且要認(rèn)為點擊一下zoom out按鈕才能呈現(xiàn)地圖,其二參數(shù)不對,在下面的代碼注釋中已有介紹,在此不做詳述了。所有的數(shù)據(jù)均為隨機(jī)值,不代表任何含義。
import json
import pandas as pd
import plotly.express as px
def print_json(data):
print(json.dumps(data, sort_keys=True, indent=4, separators=(', ', ': '), ensure_ascii=False))
with open('countries.geo.json') as response:
counties = json.load(response)
df = pd.read_csv("datarand.csv",encoding="utf-8")
# 世界地圖,不指定鍵值,默認(rèn)采用geojson中的id值,即國家簡寫,數(shù)據(jù)表格中的列也要為國家簡寫,即country列
fig = px.choropleth_mapbox(df, geojson=counties,locations='country', color='key1',
color_continuous_scale=px.colors.diverging.RdYlGn[::-1],
range_color=(100, 10000),
mapbox_style="carto-positron",
zoom=1,
center={"lat": 37.4189, "lon": 116.4219},
opacity=0.5
)
fig.update_layout(margin={"r":0,"t":0,"l":0,"b":0})
fig.show()
??
# 世界地圖,指定properties.name國家名稱作為鍵值,數(shù)據(jù)表格中的列也要改為國家,即locations列
fig = px.choropleth_mapbox(df, geojson=counties, featureidkey="properties.name",locations='name', color='key1',
color_continuous_scale="Viridis",
range_color=(100, 10000),
mapbox_style="carto-positron",
zoom=1,
center={"lat": 37.4189, "lon": 116.4219},
opacity=0.5
)
fig.update_layout(margin={"r":0,"t":0,"l":0,"b":0})
fig.show()
??
# 世界地圖,指定id國家簡寫作為鍵值,數(shù)據(jù)表格中的列也要改為國家簡寫,即country列
fig = px.choropleth_mapbox(df, geojson=counties, featureidkey="id",locations='country', color='key1',
color_continuous_scale="Reds",
range_color=(100, 10000),
mapbox_style="carto-positron",
zoom=1,
center={"lat": 37.4189, "lon": 116.4219},
opacity=0.5
)
fig.update_layout(margin={"r":0,"t":0,"l":0,"b":0})
fig.show()
??
# 世界地圖,不指定鍵值,默認(rèn)采用geojson中的id值,即國家簡寫,數(shù)據(jù)表格中的列也要為國家簡寫,即country列,對color_continuous_scale進(jìn)行設(shè)置
fig = px.choropleth_mapbox(df, geojson=counties, locations='country', color='key1',
range_color=(100, 10000),
color_continuous_scale=[
[0, 'lightcoral'], # 這個必須要寫,否則會出錯
[1. / 3000, 'indianred'],
[1. / 300, 'brown'],
[1. / 30, 'firebrick'],
[1 / 3, 'maroon'],
[1., 'darkred']],
zoom=1,
center={"lat": 37.4189, "lon": 116.4219},
mapbox_style='carto-positron')
fig.update_layout(margin={"r": 0, "t": 0, "l": 0, "b": 0})
fig.show()
??
# 中國地圖
with open('china_geo.json') as response:
counties = json.load(response)
df = pd.read_csv("data.csv",encoding="utf-8",
dtype={"areacode": str})
fig = px.choropleth_mapbox(df, geojson=counties, featureidkey="properties.adcode",locations='areacode', color='confirm',
#color_continuous_scale="Viridis",
range_color=(1, 80000),
color_continuous_scale=[
[0, 'lightcoral'], # 這個必須要寫,否則會出錯
[1. / 3000, 'indianred'],
[1. / 300, 'brown'],
[1. / 30, 'firebrick'],
[1 / 3, 'maroon'],
[1., 'darkred']],
zoom=3, center={"lat": 37.4189, "lon": 116.4219},
mapbox_style='carto-positron')
fig.update_layout(margin={"r": 0, "t": 0, "l": 0, "b": 0})
fig.show()
??
# 海南地圖
with open('460000-hainan.json') as response:
counties = json.load(response)
df = pd.read_csv("hainandata.csv",encoding="utf-8",
dtype={"areacode": str})
fig = px.choropleth_mapbox(df, geojson=counties, featureidkey="properties.adcode",locations='areacode', color='confirm',
# color_continuous_scale="Geyser",
color_continuous_scale='Reds',
#color_continuous_scale=px.colors.diverging.RdYlGn[::-1],
range_color=(1, 1500),
zoom=6, center={"lat": 20.031971, "lon": 110.33119},
mapbox_style='carto-positron')
fig.update_layout(margin={"r": 0, "t": 0, "l": 0, "b": 0})
fig.show()