Phonopy专题

Phonopy 后端、HDF5与低频精度

用本集群真实Si16 DFPT力常数比较C与Rust,演示HDF5矩阵、频率、网格和低频舍入。

更新于 2026-11-06约 6 分钟阅读按任务与环境选择适用配置
阅读本篇目录

下载输入、力常数、转换脚本与绘图资料包。在已分配的 CPU 资源内解压,一份新目录运行一次:

unzip phonopy-special-formats-wave241-*.zip -d phonopy-practice
cd phonopy-practice
bash run.sh
ls analysis figures

run.sh 每次使用 1 个 CPU,不需要 GPU。它完成结构生成、原生格式转换、读回比较和既有 Si 力常数后处理,最后得到 CSV 和三张高清图;不会启动 VASP 或其他电子结构程序。输出目录已存在时,另解压到新目录继续练习。

环境为 phonopy/4.8.3、Python 3.11.16、NumPy 2.3.5、SciPy 1.16.3、spglib 2.7.0;C/OpenMP 部分使用 GCC 13.3,默认 Rust 后端为 phonors 0.6.0。CRYSTAL 外部几何独立读回使用集群的 ASE 3.29.0 环境。后面的短命令在 module load phonopy/4.8.3 后使用。

1. 本例从哪一步开始#

本例使用本集群已经完成的Si16 VASP DFPT数值力常数,不重新求DFT。超胞16个原子、原胞2个原子,源计算为VASP6.5.1 CPU版、IBRION=8、2×2×2电子k网格。完整DFPT工作流见qvasp与Phonopy声子。这是小体系操作参考,不把一次小网格计算称作材料收敛数据。

从 inputs/Si16/phonopy_disp.yaml 和 FORCE_CONSTANTS 读入、生成完整数据文件后,分别用默认Rust和C后端计算相同的6个q点、4×4×4声子网格;保持原始力常数,不对称化、不额外施加ASR、不裁掉负频。

2. 准备同一份数据#

完整执行 bash run.sh 后,也可从初始解压目录单独准备新的手动目录:

mkdir manual-backend
cp work/backends/complete.yaml manual-backend/phonopy.yaml
cd manual-backend

complete.yaml 包含结构与力常数。本例先加载数值文件再保存,所用Python方法:

import phonopy
p = phonopy.load('inputs/Si16/phonopy_disp.yaml',
                 force_constants_filename='inputs/Si16/FORCE_CONSTANTS',
                 is_nac=False, symmetrize_fc=False)
p.save(filename='complete.yaml', settings={'force_constants': True})

这段路径以原始解压目录为起点。在自己的体系中,必须让结构、超胞矩阵、原子顺序与力常数完全匹配;只复制一个FORCE_CONSTANTS而换了结构,程序能运行也未必有物理意义。

3. 默认Rust与C怎么选择#

在新练习目录先运行默认Rust:

phonopy phonopy.yaml --no-fc-symmetry --nonac \
  --qpoints '0 0 0 .5 0 .5 .1 .2 .3 .5 .5 .5 .5 .25 .75 .25 .25 .25' \
  --qpoints-format hdf5 --writedm --eigenvectors \
  --writefc --writefc-format hdf5
mv qpoints.hdf5 qpoints-Rust.hdf5

再指定C后端:

phonopy phonopy.yaml --legacy-backend --no-fc-symmetry --nonac \
  --qpoints '0 0 0 .5 0 .5 .1 .2 .3 .5 .5 .5 .5 .25 .75 .25 .25 .25' \
  --qpoints-format hdf5 --writedm --eigenvectors
mv qpoints.hdf5 qpoints-C.hdf5

4.8.3默认已经使用Rust。--rust在这个版本是弃用的空操作参数,选择C用--legacy-backend。这与VASP用CPU还是GPU没有关系,也不改变源力常数来自哪次电子结构计算。

4. 直接提取HDF5频率#

python - <<'PYCODE'
import h5py
import numpy as np
with h5py.File('qpoints-Rust.hdf5') as h:
    print('datasets:', list(h.keys()))
    q = h['qpoint'][:]
    f = h['frequency'][:]
with h5py.File('qpoints-C.hdf5') as h:
    fc = h['frequency'][:]
print('qpoints:', q.shape)
print('frequencies:', f.shape)
print('max difference / THz:', np.max(np.abs(f-fc)))
np.savetxt('frequencies.csv', np.c_[q, f], delimiter=',',
           header='qx,qy,qz,f1,f2,f3,f4,f5,f6', comments='')
PYCODE

本例q点数组为(6,3),频率为(6,6)。实测C/Rust频率最大差约3.24×10⁻¹⁰ THz;完整64点网格的差也约3.24×10⁻¹⁰ THz。不同输出格式的小数位数会让末位略有差别,不能据此宣称某个后端提高了材料计算精度。

Si实际力常数的C/Rust频率和64点网格差值

左图是六个独立q点的六支频率,用线辅助辨认分支,不是高对称能带路径。右图逐个网格q点比较两后端,原始CSV和绘图脚本在资料包中。

5. 为什么很小的Γ点负频要看全精度矩阵#

本例Γ点三支声学模约为−1.0×10⁻⁴ THz,即约−0.00334 cm⁻¹。保留它们是为了展示原始数值,不代表判定硅存在真实动力学不稳定性。物理判断还要检查超胞、电子精度、声学和规则、网格与适当的对称化处理。

原生YAML动力学矩阵显示到10位小数时,极小的本征值可能在打印中被舍入掉;用这张文本矩阵重新对角化会得到零附近的数,与原生全精度频率相差约10⁻⁴ THz。这次差异来自矩阵输出精度,不能直接认为默认后端自动删除了负频。

使用HDF5的dynamical_matrix保留全精度,再独立计算本征频率即可比较。资料包实际操作:

with h5py.File('qpoints-Rust.hdf5') as h:
    dm = h['dynamical_matrix'][:]
    native = h['frequency'][:]
eigenvalue = np.linalg.eigvalsh(dm)
# 当前安装版本、当前VASP单位体系的换算系数;其他接口不能照抄。
factor = 15.633302300230191
independent = np.sign(eigenvalue) * np.sqrt(np.abs(eigenvalue)) * factor
print(np.max(np.abs(independent-native)))

换算系数应从当前Phonopy对象的p.unit_conversion_factor读取;原始数据文件中的旧版本显示值可能少几位小数。不同计算软件的力与长度单位不相同,不能一律套用VASP系数。

6. 什么时候改参数,什么时候保留原始结果#

  • 仅比较后端:结构、质量、力常数、NAC、网格、ASR等全部保持一致。
  • 关注很低的频率:保留HDF5矩阵与原始频率,别从低精度文本反推极小本征值。
  • 做热性质:先检查低频与网格收敛,再按具体物理需求处理声学模;不要为让图看起来平滑直接裁负值。
  • 求力常数:symfc/ALM是另一层求解方法,不能用切换C/Rust代替更好的位移—力数据。

本例所有数据、转换和绘图均为CPU轻量后处理;没有GPU加速比或CPU节点性能结论。官方接口单位和设置标签可进一步查询。

需要根据你的体系选择资源?联系讨论计算需求。实际可用软件与权限,以当前账户和运行环境为准。

查看配图

放大后可滚动查看细节,按 Esc 关闭。

100%查看原图 ↗