让matplotlib支持中文的更简单办法


上篇文章讨论了 dtreeviz,seaborn 和 matplotlib 的中文支持的解决办法。后来发现其实可以更简单,先上代码
from matplotlib import pyplot as plt,font_manager as fmfrom pathlib import Pathimport os#Restore the `.rcParams` from Matplotlib's internal default style.plt.rcdefaults()path = Path(os.getcwd())fname=os.path.join(path.parent.absolute(),'data','NotoSerifCJK-Regular.ttc')fontProperties=fm.FontProperties(fname=fname,size=14)default_font=fontProperties.get_name()# "Arial Unicode MS"if default_font not in [f.name for f in fm.fontManager.ttflist]:    print(f"{default_font} does not exist, let's add it to fontManager" )if fname not in [f.fname for f in fm.fontManager.ttflist]:    fm.fontManager.addfont(fname) # need absolute pathplt.rcParams['font.sans-serif']=[default_font]+plt.rcParams['font.sans-serif']plt.rcParams['axes.unicode_minus']=False # in case minus sign is shown as box
代码中所提到的字体可以从这里下载NotoSerifCJK-Regular.ttc[1],
不需要把所下载的字体安装到系统字体目录,也不需要复制到 matplotlib 字体目录, 只需要调用fontManager.addfont(fname)方法即可。
注意字体路径必须为绝对路径。
通过 FontProperties 可以获得字体名(fontname)接下来就可以正常使用了。
macOS, Linux和Windows 均支持。
上面代码执行完毕,接下来的使用方法,和把字体安装一样,
import seaborn as snsfrom matplotlib import pyplot as pltplt.rcdefaults()iris = sns.load_dataset('iris')iris.columns=['萼片sepal_length', '萼片sepal_width'              ,'花瓣petal_length', '花瓣petal_width','species']iris.replace(["setosa","versicolor","virginica"],            ["山鸢尾 (부채붓꽃)", "变色鸢尾(ブル-フラッグ)"           , "维吉尼亚鸢尾(Iris-virginica)"],            inplace=True)# style used as a theme of graph for example # if we want black graph with grid then write "darkgrid"sns.set_style("whitegrid",{"font.sans-serif":[default_font]}) sns.pairplot(iris, hue="species")
有兴趣的可以看看我写的Streamlit 和 svg 的应用(支持 CJK 版本)[2], 算是几分钟搞定一个决策树展示的 Web 应用的进阶版本。
参考资料
[1]
NotoSerifCJK-Regular.ttc: https://github.com/googlefonts/noto-cjk/raw/main/Serif/NotoSerifCJK-Regular.ttc[2]
Streamlit 和 svg 的应用(支持 CJK 版本): https://github.com/alitrack/ml/blob/main/streamlit/st_cjk_svg.py
到顶部