【发布时间】:2018-11-28 10:46:52
【问题描述】:
下面的代码应该为越南的所有州着色:
import pandas as pd
import matplotlib.pyplot as plt
from mpl_toolkits.basemap import Basemap
fig, ax = plt.subplots(figsize=(10,20))
# create the map
map = Basemap(resolution='l', # c, l, i, h, f or None
projection='merc',
lat_0=15.95, lon_0=105.85,
llcrnrlon=102., llcrnrlat= 8.31, urcrnrlon=109.69, urcrnrlat=23.61)
# load the shapefile, use the name 'states'
map.readshapefile(r'path\to\gadm36_VNM_1', name='states', drawbounds=True)
# shapefile downloaded from http://www.gadm.org/
# collect the state names from the shapefile attributes so we can
# look up the shape obect for a state by it's name
state_names = []
for shape_dict in map.states_info:
state_names.append(shape_dict['VARNAME_1'])
ax = plt.gca() # get current axes instance
# NOR, CEN, SOU and MEK are some subdivisions I have created for the states of Vietnam
NOR = ['Lai Chau',
'Lao Cai',
'Ha Giang',
'Cao Bang',
'Dien Bien',
'Son La',
'Yen Bai',
'Tuyen Quang',
'Bac Kan',
'Lang Son',
'Thai Nguyen',
'Phu Tho',
'Vinh Phuc',
'Hoa Binh',
'Ha Noi',
'Bac Ninh',
'Hai Duong',
'Hung Yen',
'Ha Nam',
'Quang Ninh',
'Hai Phong',
'Thai Binh',
'Nam Dinh',
'Bac Giang',
'Ninh Binh']
CEN = ['Thanh Hoa',
'Nghe An',
'Ha Tinh',
'Quang Binh',
'Quang Tri',
'Thua Thien Hue',
'Da Nang']
SOU = ['Quang Nam',
'Kon Tum',
'Quang Ngai',
'Gia Lai',
'Binh Dinh',
'Dak Lak',
'Phu Yen',
'Khanh Hoa',
'Dak Nong',
'Lam Dong',
'Ninh Thuan']
MEK = ['Binh Phuoc',
'Dong Nai',
'Binh Thuan',
'Tay Ninh',
'Binh Duong',
'Dong Nai',
'Ba Ria - Vung Tau',
'Ho Chi Minh',
'Long An',
'An Giang',
'Dong Thap',
'Tien Giang',
'Kien Giang',
'Can Tho',
'Vinh Long',
'Ben Tre',
'Hau Giang',
'Tra Vinh',
'Soc Trang',
'Bac Lieu',
'Ca Mau']
# Define the colours to be used to colour the states
from matplotlib import cm
from numpy import linspace
start = 0.5
stop = 1.0
number_of_lines= 4
cm_subsection = linspace(start, stop, number_of_lines)
cm_subsection[0] = cm_subsection[0]*4
cm_subsection[1] = cm_subsection[1]*0.6
cm_subsection[2] = cm_subsection[2]*0.8
cm_subsection[3] = cm_subsection[3]*0.1
colors = [ cm.Blues(x) for x in cm_subsection ]
for state in NOR:
seg = map.states[state_names.index(state)]
poly = Polygon(seg, facecolor=colors[0], edgecolor=colors[0])
ax.add_patch(poly)
for state in CEN:
seg = map.states[state_names.index(state)]
poly = Polygon(seg, facecolor=colors[1], edgecolor=colors[1])
ax.add_patch(poly)
for state in SOU:
seg = map.states[state_names.index(state)]
poly = Polygon(seg, facecolor=colors[2], edgecolor=colors[2])
ax.add_patch(poly)
for state in MEK:
seg = map.states[state_names.index(state)]
poly = Polygon(seg, facecolor=colors[3], edgecolor=colors[3])
ax.add_patch(poly)
import matplotlib.patches as mpatches
NOR_patch = mpatches.Patch(color=colors[0], label='Rate: 34.85%')
CEN_patch = mpatches.Patch(color=colors[1], label='Rate: 25.61%')
SOU_patch = mpatches.Patch(color=colors[2], label='Rate: 32.66%')
MEK_patch = mpatches.Patch(color=colors[3], label='Rate: 20.02%')
plt.legend(handles=[NOR_patch, CEN_patch, SOU_patch, MEK_patch])
plt.show()
但这会产生下面的地图,其中一些州没有着色,即使它们出现在州名和细分中:
事实上,如果我尝试为列表中不存在名称的状态着色,则会引发错误:
MEK.append('ABCDE')
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
<ipython-input-619-a89da62a0831> in <module>()
134
135 for state in MEK:
--> 136 seg = map.states[state_names.index(state)]
137 poly = Polygon(seg, facecolor=colors[3], edgecolor=colors[3])
138 ax.add_patch(poly)
ValueError: 'ABCDE' is not in list
因此,显然列表中存在未着色的状态,因为我没有收到任何错误。那么,发生了什么?
编辑:让我震惊的是,几乎所有没有颜色的州在现实世界中至少有一部分与海洋/海洋接壤。下面以红色突出显示 6 个例外:
现在这很有趣!会不会跟这个问题有关系?如果是,是什么?为什么?为什么存在这 6 个例外?
编辑 2: 我在绘制菲律宾地图时得到了类似的结果:
【问题讨论】:
-
您使用的 shapefile 是否可以从某处获得?
-
@ThomasKühn 是的,来自gadm.org。我在代码中提到了这一点。这是我唯一找到越南详细 shapefile 的地方。
-
@ThomasKühn 我在绘制菲律宾地图时也得到了类似的结果,我在问题的第二次编辑中显示了这一结果。我使用来自 gadm.org 和 philgis.org/country-basemaps/country-provinces 的 shapefile 进行了尝试,两者都产生了相同的结果(即,相同的省份没有着色)。
-
我想我找到了问题所在。请给我一分钟时间写一个答案...
标签: python matplotlib colors data-visualization matplotlib-basemap