PyWPEMPyWPEM

PyWPEM / PyXplore

中文说明书

本说明书根据 src 中的公开 API 和 Tutorial 中的 Jupyter 示例整理,覆盖 PyWPEM 常见分析流程、关键参数和输出文件。

1. 软件简介

PyWPEM 是一个用于 X 射线衍射全谱分解与结构精修的 Python 工具包。它的核心思想是把完整衍射谱看作受物理约束的概率混合分布,并在 EM 迭代中结合 Bragg 定律更新峰位置、峰形、峰权重和晶格参数。

最常用的入口来自 from PyXplore import WPEM。主要函数包括:

  • WPEM.BackgroundFit:拟合并扣除背景。
  • WPEM.CIFpreprocess:读取 CIF,生成 HKL、2θ、multiplicity 和消光峰。
  • WPEM.XRDfit:运行 WPEM 全谱拟合、分峰和晶格精修。
  • WPEM.Plot_Components:绘制分相或分峰结果。
  • WPEM.XRDSimulation:根据 CIF 模拟 XRD 图谱。
  • WPEM.SubstitutionalSearch:搜索固溶体替位结构。
  • WPEM.Amorphous_fitWPEM.AmorphousRDFun:非晶宽峰拟合与 RDF 分析。
  • WPEM.XPSfit:XPS 主峰和卫星峰的 EM 分解。

2. 安装与环境

更详细教程:Class 1 Installation

建议使用独立 conda 环境,避免和系统 Python 或其他科研软件的依赖冲突。教程中推荐 Python 3.10。

conda create -n pywpem python=3.10
conda activate pywpem
pip install notebook
pip install PyXplore
pip install --upgrade PyXplore

启动 Jupyter Notebook:

jupyter notebook

在 notebook 或 Python 脚本中测试导入:

from PyXplore import WPEM

如果网络下载较慢,可以先配置 pip 镜像源,或在网络稳定环境中安装依赖。

3. 数据准备

更详细教程:Class 2 Single-phase refinement

3.1 实验谱文件格式

XRD 输入通常是两列数据,不需要表头:第一列为 2theta,第二列为 intensity。CSV 示例:

10.000, 123.4
10.010, 125.1
10.020, 128.7

读取方式:

import pandas as pd
intensity_csv = pd.read_csv("intensity.csv", header=None)

原位 XRD 或部分仪器数据也可以使用 Excel。教程中使用:

intensity_excel = pd.read_excel("intensity.xlsx", header=None)

3.2 CIF 文件

每个候选晶相建议准备一个 CIF 文件。CIFpreprocess 会读取晶格常数、原子坐标、空间群和对称操作,并生成后续拟合需要的 HKL 文件。

latt, atom_coordinates, density = WPEM.CIFpreprocess(
    filepath="Mn2O3.cif",
    two_theta_range=(15, 75)
)

3.3 工作目录

默认情况下,PyWPEM 会在当前目录写入 ConvertedDocumentsoutput_xrdWPEMFittingResults 等输出目录。批处理时强烈建议为每个样品设置独立 work_dir,避免文件互相覆盖。

4. 单相 XRD 精修

更详细教程:Class 2 Single-phase refinement

本流程对应教程中的 Mn2O3 单相示例,适合用户第一次完整跑通 PyWPEM。

步骤 1:导入库并读取数据

from PyXplore import WPEM
import pandas as pd

intensity_csv = pd.read_csv("intensity.csv", header=None)

步骤 2:背景拟合

var = WPEM.BackgroundFit(
    intensity_csv,
    lowAngleRange=17,
    poly_n=13,
    bac_split=16,
    bac_num=300
)

该步骤会生成 ConvertedDocuments/no_bac_intensity.csvConvertedDocuments/bac.csv。如果当前工作目录就是数据目录,后续可以直接使用文件名 no_bac_intensity.csvbac.csv;如果使用 work_dir,建议使用完整路径。

步骤 3:CIF 预处理

latt, atom_coordinates, density = WPEM.CIFpreprocess(
    filepath="Mn2O3.cif",
    two_theta_range=(15, 75)
)

latt 是初始晶格常数,格式为 [a, b, c, alpha, beta, gamma]density 可用于后续质量分数估计。

步骤 4:运行 WPEM 精修

wavelength = [1.540593, 1.544414]
Lattice_constants = [latt]

WPEM.XRDfit(
    wavelength,
    var,
    Lattice_constants,
    "no_bac_intensity.csv",
    "intensity.csv",
    "bac.csv",
    subset_number=11,
    low_bound=20,
    up_bound=70,
    bta=0.85,
    iter_max=5,
    asy_C=0,
    InitializationEpoch=0
)

关键参数解释

  • wavelength:X 射线波长。Cu Kα1/Kα2 常用 [1.540593, 1.544414]
  • subset_number:用于 Bragg 晶格更新的峰数量。
  • low_boundup_bound:选择参与晶格更新的 2θ 范围。
  • bta:伪 Voigt 函数中 Lorentzian 分量比例。
  • iter_max:最大迭代次数。首次测试可以设小一些,正式分析可适当增大。
  • InitializationEpoch:初始化阶段冻结峰位置的轮数。

5. 多相 XRD 精修

更详细教程:Class 3 Multiphase refinement

多相流程和单相类似,区别是每个候选相都需要运行 CIFpreprocess,并把多个晶格常数组成列表传给 XRDfit

from PyXplore import WPEM
import pandas as pd

intensity_csv = pd.read_csv("intensity.csv", header=None)
Var = WPEM.BackgroundFit(
    intensity_csv,
    LFctg=0.2,
    lowAngleRange=20,
    window_length=7,
    bac_num=500
)

NaCl, _, density_nacl = WPEM.CIFpreprocess("NaCl.cif", two_theta_range=(11, 110))
LiCO, _, density_lico = WPEM.CIFpreprocess("Li2CO3.cif", two_theta_range=(11, 110))

wavelength = [1.540593, 1.544414]
WPEM.XRDfit(
    wavelength,
    Var,
    [NaCl, LiCO],
    "no_bac_intensity.csv",
    "intensity.csv",
    "bac.csv",
    subset_number=11,
    low_bound=20,
    up_bound=50,
    bta=0.9,
    iter_max=5,
    asy_C=0,
    InitializationEpoch=2,
    num=7,
    Ave_Waves=True
)

WPEM.Plot_Components(
    lowboundary=10,
    upboundary=110,
    wavelength=wavelength,
    name=["NaCl", "Li2CO3"],
    phase=2
)

phase=2 表示绘制两个晶相的分解结果。name 的顺序应与 Lattice_constants 中的相顺序一致。

6. XRD 模拟

更详细教程:Class 4 XRD simulations

XRDSimulation 用 CIF 文件生成模拟谱,可用于相鉴定后的验证,也可构造带扰动的训练或测试数据。

FHKL_square, two_theta_sim, intensity_sim = WPEM.XRDSimulation(
    filepath="PSO.cif",
    two_theta_range=(10, 120, 0.01),
    bacI=True,
    GrainSize=30,
    orientation=[-0.1, 0.1],
    thermo_vib=0.1,
    zero_shift=0.01
)
  • two_theta_range=(start, stop, step) 控制模拟角度范围和步长。
  • GrainSize 用于模拟晶粒尺寸导致的峰宽变化。
  • orientation 用于模拟择优取向导致的强度扰动。
  • thermo_vib 用于模拟原子平均位置的热振动扰动。
  • zero_shift 用于模拟仪器零点偏移。
  • bacI=True 会加入随机多项式背景。

7. 原位 XRD 批处理

更详细教程:Class 5 In situ XRD

原位或 operando XRD 通常包含大量连续谱。推荐给每个谱建立独立临时目录,把输入文件和必要的 peak0.csv 放入该目录,并通过 work_dir 控制输出位置。

import os
import shutil
import pandas as pd
from PyXplore import WPEM

wavelength = [1.540593, 1.544414]
Lattice_constants = [[2.87549, 2.87549, 14.02056, 90.0, 90.0, 120.0]]
results = {}
num_samples = 5

for i in range(num_samples):
    idx = i + 1
    tmp_dir = f"tmp/{idx}"
    os.makedirs(tmp_dir, exist_ok=True)

    tmp_intensity = os.path.join(tmp_dir, "intensity.xlsx")
    shutil.copyfile(f"data/{idx}.xlsx", tmp_intensity)
    shutil.copyfile("peak0.csv", os.path.join(tmp_dir, "peak0.csv"))

    intensity_excel = pd.read_excel(tmp_intensity, header=None)
    var = WPEM.BackgroundFit(
        intensity_excel,
        lowAngleRange=17,
        LFctg=0.0,
        poly_n=8,
        bac_split=10,
        bac_num=80,
        work_dir=tmp_dir
    )

    no_bac_file = os.path.join(tmp_dir, "ConvertedDocuments", "no_bac_intensity.csv")
    bac_file = os.path.join(tmp_dir, "ConvertedDocuments", "bac.csv")

    duration, lattice = WPEM.XRDfit(
        wavelength,
        var,
        Lattice_constants,
        no_bac_file,
        tmp_intensity,
        bac_file,
        Ave_Waves=True,
        subset_number=6,
        low_bound=15,
        up_bound=60,
        bta=0.85,
        iter_max=3,
        asy_C=0,
        InitializationEpoch=0,
        work_dir=tmp_dir
    )
    results[idx] = lattice

批处理完成后,可以把每个样品的晶格参数整理成 Excel 或 CSV,再绘制随时间、温度、电压或循环次数变化的曲线。

8. 固溶体搜索

更详细教程:Class 6 Solid solution searching

固溶体流程通常先做一次 XRD 精修,得到某一晶相的 WPEM 输出文件,再用 SubstitutionalSearch 搜索可能的替位结构。

WPEM.SubstitutionalSearch(
    xrd_pattern="CrystalSystem0_WPEMout_2026.6.10_11.1.csv",
    cif_file="Mn2O3.cif",
    random_num=20,
    wavelength="CuKa",
    search_cap=20,
    SolventAtom="Mn3+",
    SoluteAtom="Ru2+",
    max_iter=15,
    cal_extinction=False
)

搜索完成后,可用 XRDSimulation 对候选结构进行模拟,并与实验谱或 WPEM 分解谱比较。

9. 非晶分析

更详细教程:Class 7 Amorphous study

非晶样品通常包含晶体峰和非晶宽峰。推荐先用 XRDfit 分解晶体峰,再用 Amorphous_fit 拟合剩余宽峰,最后可计算 RDF。

wavelength = [1.03]
Lattice_constants = [[17.53, 17.53, 6.47, 90, 90, 120]]

WPEM.XRDfit(
    wavelength,
    var,
    Lattice_constants,
    "no_bac_intensity.csv",
    "intensity.csv",
    "bac.csv",
    subset_number=3,
    low_bound=6,
    up_bound=16,
    bta=0.78,
    iter_max=10,
    asy_C=0,
    InitializationEpoch=0
)

WPEM.Amorphous_fit(
    mix_component=2,
    sigma2_coef=0.5,
    max_iter=200,
    peak_location=None,
    Wavelength=1.03
)

WPEM.Plot_Components(
    lowboundary=4,
    upboundary=19,
    wavelength=wavelength,
    Macromolecule=True,
    phase=1
)

WPEM.AmorphousRDFun(
    wavelength=1.03,
    r_max=4,
    density_zero=None,
    Nf2=1,
    highlight=6
)

mix_component 是非晶宽峰数量。若已知道宽峰大致位置,可用 peak_location=[20, 30, "fixed"] 固定初始峰位。

10. XPS 分解

更详细教程:Class 8 X-Ray spectrograph

PyWPEM 也包含 XPS 的 EM 分解模块。XPS 数据同样是两列:binding energy 和 intensity。通常先用 XPS 模式拟合背景,再定义主峰和卫星峰。

from PyXplore import WPEM
import pandas as pd

intensity_csv = pd.read_csv("CuO.csv", header=None)
var = WPEM.BackgroundFit(
    intensity_csv,
    segement=[[910, 931], [948, 952], [958, 959], [966, 970]],
    bac_num=120,
    Model="XPS",
    noise=0.05,
    bac_var_type="multivariate gaussian"
)

AtomIdentifier = [
    ["CuII", "2p3/2", 933.7],
    ["CuII", "2p1/2", 954]
]

satellitePeaks = [
    ["CuII", "2p3/2", 941.6],
    ["CuII", "2p3/2", 943.4],
    ["CuII", "2p1/2", 962.5]
]

WPEM.XPSfit(
    var,
    AtomIdentifier,
    satellitePeaks,
    "no_bac_intensity.csv",
    "CuO.csv",
    "bac.csv",
    bta=0.80,
    iter_max=50
)

AtomIdentifier 用于定义主峰,格式为 [化学态, 轨道, 初始结合能]satellitePeaks 用于定义卫星峰。

11. 输出文件

目录或文件说明
ConvertedDocuments/no_bac_intensity.csv扣除背景后的实验谱。
ConvertedDocuments/bac.csv拟合得到的背景曲线。
output_xrd/*HKL.csvCIF 预处理生成的 HKL、d 间距、2θ 和 multiplicity。
output_xrd/*Extinction_peak.csv系统消光峰。
WPEMFittingResultsXRD 拟合曲线、峰参数、晶相分解结果、质量分数估计和模型参数。
DecomposedComponents分峰曲线、更新背景、非晶分解结果。
Simulation_WPEMXRD 模拟谱、结构因子和 VASP 结构文件。
XPSFittingProfileXPS 拟合曲线和峰参数。
XPScomponentsXPS 分峰组分曲线。

12. 常见问题

文件长度不匹配

XRDfit 要求原始谱、扣背景谱和背景谱的点数一致。若出现不匹配,重新运行 BackgroundFit,并确认后续读取的是同一目录下生成的 no_bac_intensity.csvbac.csv

峰位整体偏移

检查波长是否正确、仪器是否存在零点偏移。必要时测试 ZeroShift=True 或在模拟中设置 zero_shift 理解偏移方向。

多相结果顺序混乱

Lattice_constantsdensity_listname 和输出晶相编号必须保持同一顺序。

批处理结果被覆盖

为每个样品设置独立 work_dir。原位教程采用 tmp/1tmp/2 这类结构,就是为了隔离输出。

背景拟合不理想

调整 LFctglowAngleRangebac_splitbac_numpoly_n。XPS 场景可使用 segement 手动指定背景区间。