在 Linux 环境下解决 Matplotlib 中文字体显示问题: UserWarning: findfont: Font family ‘SimHei‘ not found

问题描述

在使用 Python 的 Matplotlib 库绘图时,当需要显示中文字符(如标题、标签或图例)时,经常会遇到以下警告:

UserWarning: findfont: Font family 'SimHei' not found.

即使已经正确安装了中文字体,这个警告仍可能出现,导致图表中的中文显示为方框或乱码。本文将详细介绍这个问题的原因和解决方法。

问题原因

这个问题通常有以下几个原因:

  1. 字体未安装:系统中没有安装 ‘SimHei’(黑体)等中文字体。
  2. 字体已安装但 Matplotlib 无法识别:这是最常见的情况,即使使用 fc-list 命令可以看到字体已安装,但 Matplotlib 的字体缓存没有正确更新。
  3. 字体路径配置不正确:Matplotlib 的字体搜索路径没有包含自定义字体目录。

解决方案

方案一:安装中文字体

首先,确保系统中已安装中文字体。

Ubuntu/Debian 系统:
sudo apt-get update
sudo apt-get install -y fonts-wqy-microhei fonts-wqy-zenhei xfonts-wqy
CentOS/RHEL 系统:
sudo yum install -y wqy-microhei-fonts wqy-zenhei-fonts

方案二:手动添加中文字体

如果需要特定的中文字体(如 SimHei),可以手动添加:

  1. 创建用户字体目录:
mkdir -p ~/.fonts
  1. 将字体文件复制到该目录:
# 假设您已经有 SimHei.ttf 文件
cp SimHei.ttf ~/.fonts/
# 或者为了明确区分
cp SimHei.ttf ~/.fonts/chinese.simhei.ttf
  1. 刷新字体缓存:
fc-cache -fv
  1. 验证字体安装成功:
fc-list | grep -i simhei

如果成功,将显示类似以下的输出:

/home/user/.fonts/SimHei.ttf: 黑体,SimHei:style=Regular

方案三:清除 Matplotlib 字体缓存(关键步骤)

即使字体已正确安装,Matplotlib 仍可能无法识别它,这是最常见的问题。解决方法是清除 Matplotlib 的字体缓存:

rm -rf ~/.cache/matplotlib

这将强制 Matplotlib 在下次使用时重新扫描系统字体。

方案四:在代码中正确设置字体

在 Python 代码中,可以通过以下方式设置中文字体:

import matplotlib.pyplot as plt
from matplotlib.font_manager import FontProperties

# 方法一:直接设置字体
plt.rcParams['font.sans-serif'] = ['SimHei']  # 用黑体显示中文
plt.rcParams['axes.unicode_minus'] = False  # 正确显示负号

# 方法二:使用 FontProperties
font = FontProperties(fname='/path/to/SimHei.ttf', size=14)
plt.title('中文标题', fontproperties=font)

方案五:编写健壮的字体选择函数

为了增强代码的健壮性,可以实现一个函数来尝试多种中文字体:

from matplotlib.font_manager import FontProperties

def get_font_properties():
    """获取可用的字体属性,尝试依次使用中文字体"""
    # 尝试多种中文字体,按优先级排序
    font_names = ['SimHei', 'Microsoft YaHei', 'SimSun', 'NSimSun', 'FangSong', 'KaiTi', 'Arial Unicode MS']
    
    # 创建临时字体属性来测试
    font_prop = FontProperties()
    
    # 尝试设置每种字体,直到找到系统上可用的字体
    for font_name in font_names:
        try:
            font_prop.set_family(font_name)
            print(f"使用字体: {font_name}")
            return font_prop
        except:
            continue
    
    # 如果以上都失败,使用默认字体
    print("未找到合适的中文字体,将使用系统默认字体")
    return None

# 使用字体
font_prop = get_font_properties()
if font_prop:
    plt.rcParams['font.family'] = font_prop.get_family()

实际案例:解决 SimHei 字体警告

我们曾在一个项目中遇到了类似问题,尽管已经安装了 SimHei 字体并且 fc-list 能够找到它,但 Matplotlib 仍然报出警告。

问题诊断

  1. 首先确认字体是否已安装:
fc-list | grep -i simhei

输出:

/home/user/.fonts/chinese.simhei.ttf: 黑体,SimHei:style=Regular
/home/user/.fonts/SimHei.ttf: 黑体,SimHei:style=Regular
  1. 检查 Matplotlib 是否能识别这些字体:
python -c "import matplotlib.font_manager as fm; print([f.name for f in fm.fontManager.ttflist if 'simhei' in f.name.lower()])"

初始输出为空列表 [],表明 Matplotlib 无法识别这些字体。

解决步骤

  1. 清除 Matplotlib 的字体缓存:
rm -rf ~/.cache/matplotlib
  1. 再次检查 Matplotlib 能否识别字体:
python -c "import matplotlib.font_manager as fm; print([f.name for f in fm.fontManager.ttflist if 'simhei' in f.name.lower()])"

现在输出为 ['SimHei', 'SimHei'],表明 Matplotlib 已成功识别字体。

  1. 运行绘图脚本,确认不再出现警告,且中文显示正常。

常见问题与解决方法

  1. 问题:清除缓存后仍然无法识别字体
    解决:检查字体文件是否损坏,尝试重新下载或使用其他中文字体。

  2. 问题:部分字符显示为方框
    解决:确保选择的字体包含所需的所有字符集。

  3. 问题:在容器或虚拟环境中运行时字体问题
    解决:需要在容器中安装字体,或将字体文件挂载到容器中。

总结

解决 Matplotlib 中文字体显示问题的关键步骤是:

  1. 确保系统安装了所需的中文字体
  2. 清除 Matplotlib 的字体缓存(通常这是最关键的步骤)
  3. 在代码中正确设置字体

通过以上步骤,可以解决大多数 Matplotlib 中文显示问题,使图表正常显示中文字符。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值