plt.fill_between报错ufunc 'isfinite'不支持输入类型解决方案
matplotlib调用fill_between绘图时ufunc 'isfinite' 类型报错解决方案
报错根因
触发该错误的核心是类型不兼容:
- 你转换字段类型时使用的
Int64(首字母大写)是pandas特有的可空整数类型,属于pandas自定义的扩展类型,并非numpy原生支持的数值类型,numpy的底层计算函数(包括报错信息里的np.isfinite)无法直接识别该类型。 - matplotlib绘图前会调用numpy的校验逻辑检查输入值是否合法,传入pandas自定义的
Int64类型数组时就会触发该类型错误。 - 你仅对
Year字段做了类型转换,但聚合后生成的Number of Immigrants列仍然是pandasInt64类型,这是触发报错的直接来源。 - 原代码还缺失numpy库的导入,后续调用
np.min/np.max时会额外触发NameError。
修复方案
将所有传入matplotlib的绘图序列转换为numpy原生支持的数值类型(int64/float64,注意类型名首字母小写)即可,不要直接传入pandas自定义的Nullable扩展类型。
修正后的可运行完整代码:
import pyodbc import pandas as pd import numpy as np # 补全缺失的numpy导入 import matplotlib.pyplot as plt import warnings warnings.filterwarnings('ignore') conn = pyodbc.connect('Driver={SQL Server Native Client 11.0};' 'Server=LAPTOP-34VQMBK6\SQLEXPRESS;' 'Database=Portofolio Data Analytics;' 'Trusted_Connection=yes;') df = pd.read_sql_query('SELECT * FROM vCanada2', conn) # 转换为numpy原生int64类型,不要使用大写I的pandas自定义Int64 df['NumOfImm'] = df['NumOfImm'].astype('int64') df = df.groupby('Year').agg({'NumOfImm': sum}).rename(columns={'NumOfImm': 'Number of Immigrants'}).reset_index() # 提取绘图数据时统一转numpy原生类型 x = df['Year'].astype('int64').values y1 = df['Number of Immigrants'].astype('int64').values fig, ax = plt.subplots(1, 1, figsize=(20,8), dpi= 120) plt.fill_between(x, y1=y1, y2=-y1, alpha=0.5, linewidth=2, color='seagreen') plt.ylim(-280000, 280000) plt.title('Immigration Rate in Canada (Two Side View)', fontsize=16) # 修正原代码中Canda的拼写错误 plt.hlines(y=0, xmin=np.min(x), xmax=np.max(x), linewidth=.5) plt.show()
注意事项
- 如果原始数据中存在空值,先调用
df = df.dropna(subset=['Year','NumOfImm'])丢弃对应空值行,再做类型转换,避免转numpy原生类型时触发报错。 - 所有基于numpy实现的Python绘图库(matplotlib、seaborn等),传参时优先使用numpy原生数值数组、Python原生int/float列表,尽量避免直接传入pandas自定义的Nullable扩展类型(
Int64/Float64/Boolean等),否则很容易触发这类类型不兼容问题。
内容的提问来源于stack exchange,提问作者Grha Gandana P
相关产品推荐
相关产品推荐

