DeepLabCut `analyze_videos` 视频推理 API 完全指南:参数详解与 TensorFlow/PyTorch 双引擎实现

原创2026-10-03 19:15:45752 阅读
文章标签:人工智能深度学习计算机视觉科研

DeepLabCut analyze_videos 视频推理 API 完全指南:参数详解与 TensorFlow/PyTorch 双引擎实现

本篇文章围绕 DeepLabCut 官方 API 参考文档 deeplabcut.analyze_videos.rst 所指向的核心函数 deeplabcut.compat.analyze_videos,系统讲解如何在训练好的网络上对视频进行姿态推理:从函数签名、全部参数语义、引擎自动分派机制,到单/多动物项目的输出产物与跟踪拼接流程。读完本文,你将能独立配置并运行视频分析,理解每个参数对推理行为与产出的实际影响,并掌握 TensorFlow 与 PyTorch 两套引擎的差异化用法。

一、API 定位与整体架构

在 DeepLabCut 3.x 中,analyze_videos 是"用训练好的网络对视频做预测"的统一入口。文档中的 .rst 文件仅是一行 Sphinx 指令 .. autofunction:: deeplabcut.compat.analyze_videos(见 docs/api/deeplabcut.analyze_videos.rst),它把最终渲染的完整内容委托给 deeplabcut/compat.py 中同名函数的 docstring。因此本文讲解的就是这个函数本体,及其背后的真实调用链。

从源码结构看,该函数是典型的"兼容层(compat layer)"设计:

  • 对外:它被导入并列入公开 API,见 deeplabcut/init.py(第 37、213 行),因此项目中既可以直接 import deeplabcut 后调用 deeplabcut.analyze_videos(...),也可以调用 deeplabcut.compat.analyze_videos(...);
  • 对内:它根据项目 shuffle 所属的引擎(TensorFlow 或 PyTorch)将调用转发到两个独立实现:

此外,函数顶部带有两个重命名装饰器(@renamed_parameter),用于兼容旧版本参数名:

  • 旧参数 batchsize → 新参数 batch_size(自 3.0.0 起);
  • 旧参数 videotype → 新参数 video_extensions(自 3.0.0 起)。

二、函数签名与完整参数参考

完整的函数签名如下(取自 deeplabcut/compat.py 第 579–608 行):

def analyze_videos(
    config: str | Path,
    videos: list[str | Path],
    video_extensions: str | Sequence[str] | None = None,
    shuffle: int = 1,
    trainingsetindex: int = 0,
    gputouse: str | None = None,
    save_as_csv: bool = False,
    in_random_order: bool = True,
    destfolder: str | Path | None = None,
    batch_size: int | None = None,
    cropping: list[int] | None = None,
    TFGPUinference: bool = True,
    dynamic: tuple[bool, float, int] = (False, 0.5, 10),
    modelprefix: str = "",
    robust_nframes: bool = False,
    allow_growth: bool = False,
    use_shelve: bool = False,
    auto_track: bool = True,
    n_tracks: int | None = None,
    animal_names: list[str] | None = None,
    calibrate: bool = False,
    identity_only: bool = False,
    use_openvino: str | None = None,
    engine: Engine | None = None,
    overwrite: bool = False,
    **torch_kwargs,
) -> str:

函数返回 str 类型的 DLCScorer——即本次用于分析视频的评分器(scorer)名称,后续 create_labeled_video、plot_trajectories 等下游函数也需要使用同一 scorer 定位产物。

下表汇总了全部参数及其含义、默认值与适用引擎:

参数 默认值 作用 引擎
config — config.yaml 项目的完整路径 通用
videos — 视频完整路径列表,或一个目录路径(目录内所有同扩展名视频) 通用
video_extensions None 视频扩展名过滤规则,见下文"输入处理" 通用
shuffle 1 训练所用数据集的 shuffle 索引 通用
trainingsetindex 0 使用 TrainingFraction 列表中的第几个(0 起始) 通用
gputouse None 仅 TF 引擎;指定 GPU 编号(对照 nvidia-smi),无 GPU 传 None TF
save_as_csv False 额外把预测导出为 .csv(多动物且 auto_track=True 时由 stitch_tracklets 保存) 通用
in_random_order True 传入视频目录时是否随机顺序分析 通用
destfolder None 分析数据输出目录,默认与视频同目录;后续分析也须传同一目录 通用
batch_size None 推理批大小;PyTorch 引擎当前不支持,传值会覆盖 pose_cfg.yaml TF
cropping None 裁剪坐标 [x1, x2, y1, y2],作用于全部视频 通用
TFGPUinference True 仅 TF 引擎;用 TensorFlow 代码在 GPU 上推理 TF
dynamic (False, 0.5, 10) 动态裁剪三元组 (state, detectiontreshold, margin) 通用
modelprefix "" 存放 DLC 模型的目录;默认在项目目录内寻找 通用
robust_nframes False 逐帧读取视频以获得可靠帧数(较慢,抗文件损坏) 通用
allow_growth False 仅 TF 引擎;小显存 GPU 上让显存按需增长而非预分配 TF
use_shelve False 用 shelf(pickle 持久化数据库)边推理边落盘,内存占用恒定 通用
auto_track True 多动物项目自动执行跟踪与拼接,产出最终 .h5 多动物
n_tracks None 要重建的轨迹数量;默认取 config.yaml 中个体数 多动物
animal_names None 指定个体命名列表;与 n_tracks 存在长度约束 多动物
calibrate False 用训练数据校准个体组装流程,增强对错误骨架链接的鲁棒性 多动物
identity_only False 模型已学习个体身份时,组装与跟踪仅依赖身份预测 多动物
use_openvino None 仅 TF 引擎;环境装有 OpenVINO 时传 "CPU" 用 CPU 推理 TF
engine None 覆盖 shuffle 的引擎(一般不应手动指定,默认从元数据加载) 通用
overwrite False 仅 PyTorch 引擎;对已有预测文件的视频重新分析 PyTorch
torch_kwargs {} 透传给 PyTorch API 的额外参数,如 device(指定 CUDA 设备) PyTorch

三、引擎自动分派机制

analyze_videos 最核心的设计是引擎分派。当 engine=None 时,函数通过 get_shuffle_engine(read_config(config), trainingsetindex=..., shuffle=..., modelprefix=...) 从项目配置与元数据中读取该 shuffle 实际使用的引擎(见 deeplabcut/compat.py 第 783–789 行):

if engine is None:
    engine = get_shuffle_engine(
        read_config(config),
        trainingsetindex=trainingsetindex,
        shuffle=shuffle,
        modelprefix=modelprefix,
    )

随后分别进入两个分支:

  • TF 分支:调用 deeplabcut.pose_estimation_tensorflow.analyze_videos,并透传 batchsize=batch_size(兼容层把新参数名映射回 TF API 的旧名)、cropping、TFGPUinference、dynamic、robust_nframes、allow_growth、use_shelve、auto_track、n_tracks、animal_names、calibrate、identity_only 等;只有显式传入 use_openvino 时才透传该参数(否则走 TF API 自身默认值);
  • PyTorch 分支:调用 deeplabcut.pose_estimation_pytorch.apis.analyze_videos。兼容层会先处理两件事:
    1. 若同时传了 gputouse,则通过 _update_device(gputouse, torch_kwargs) 把它映射为 PyTorch 的 device 参数;
    2. 若 batch_size 非空,把它并入 torch_kwargs["batch_size"];若用户已通过 torch_kwargs 传过 batch_size,则打印提示并以 torch_kwargs 中的值为准。

若两个引擎都不匹配,函数以 raise NotImplementedError(f"This function is not implemented for {engine}") 结束。这意味着:用户一般无需关心引擎,DeepLabCut 会按 shuffle 元数据自动选择正确实现;手动传 engine 属于高级用法,官方不建议(docstring 明确说明 "this should generally not be done")。

四、视频输入处理

videos 参数接受两种形式:单个/多个视频文件路径,或一个目录路径。video_extensions 控制按扩展名过滤,两条规则需要区分(compat 层与两个引擎的 docstring 描述一致):

  • video_extensions=None(默认):文件路径按原样接受;目录会被扫描,筛选出可识别的视频扩展名文件;
  • video_extensions 为 str 或 Sequence[str](例如 "mp4" 或 ["mp4", "avi"]):文件路径与目录内容都会按给定扩展名过滤。

在 PyTorch 引擎中,collect_video_paths(videos, extensions=video_extensions, shuffle=in_random_order) 负责收集与排序视频(见 deeplabcut/pose_estimation_pytorch/apis/videos.py 第 543 行);in_random_order=True 仅当传入的是目录时才有意义。

cropping 参数若给出,则对所有视频统一使用 [x1, x2, y1, y2] 坐标裁剪;若不同视频需要不同裁剪区域,则应对单个视频分别调用。PyTorch 实现中还有一层联动:当 cropping 为 None 且项目配置里 cropping 为真时,会读取配置中的 x1/x2/y1/y2(见同一文件第 441–447 行)。

五、推理执行细节与输出产物

1. 输出格式

预测结果以 MultiIndex Pandas 数组 的形式保存:索引包含网络名(scorer)、身体部位名、坐标 (x, y)(像素)以及每个部位每个帧的似然值(likelihood)。默认以高效的 HDF 格式(.h5)存放在视频所在目录;若 save_as_csv=True,则额外导出 .csv,可直接导入 MATLAB、R、Prism 等软件。

2. 网络快照的选择

"用哪个训练好的网络"由 config.yaml 中的参数(尤其是 snapshotindex)决定。PyTorch 引擎额外提供 snapshot_index 与 detector_snapshot_index(仅 top-down 模型)用于覆盖配置:索引从 0 开始,-1 表示最后一个快照,例如 snapshot-0.pt、snapshot-50.pt、snapshot-100.pt、snapshot-best.pt 中索引 1 对应 snapshot-50.pt;若传 None,则从项目配置加载。对应解析逻辑见 deeplabcut/pose_estimation_pytorch/apis/videos.py 第 434–439 行。

3. 动态裁剪(dynamic cropping)

dynamic=(state, detectiontreshold, margin) 三元组控制动态裁剪:

  • 当 state=True 时启用;
  • 若检测到目标(即任一身体部位似然 > detectiontreshold),则根据所有部位的最小/最大 x、y 计算目标边界;
  • 边界按 margin 向外扩展,此后只分析该裁剪窗内的姿态,直到目标丢失(低于 detectiontreshold);
  • 当前位置会用于更新下一帧的裁剪窗——因此 margin 必须足够大,以覆盖动物的移动幅度。

需要特别注意的是 PyTorch 引擎的约束:动态裁剪只适用于 bottom-up 姿态模型。若模型不是 bottom-up,PyTorch 实现会打印提示并关闭动态裁剪,并建议改用 top_down_dynamic 参数配合 top-down 模型使用(见 deeplabcut/pose_estimation_pytorch/apis/videos.py 第 470–488 行)。

4. 内存与帧数

  • use_shelve=True 时,数据不再在分析结束时统一 dump 成 pickle,而是边推理边写入 shelf(基于 pickle 的持久化、数据库式对象),内存占用恒定。PyTorch 实现中会创建 ShelfWriter,并在 video_inference 期间打开/关闭(见同一文件第 564–570、222–229 行)。
  • robust_nframes=True 时逐帧读取视频统计帧数,不依赖元数据,因而对文件损坏更鲁棒,但更慢;PyTorch 引擎通过 video.get_n_frames(robust=robust_nframes) 调用(第 205 行)。
  • 若处理帧数与元数据不符,PyTorch 引擎会打印警告,提示视频可能损坏,建议重新编码视频(deeplabcut/pose_estimation_pytorch/apis/videos.py 第 231–239 行)。

5. 批量与跳过机制

  • batch_size 默认取 pose_cfg.yaml 或项目配置中的值(PyTorch 引擎默认 project_cfg.get("batch_size", 1),见第 459–460 行);
  • PyTorch 引擎的 overwrite=False(默认)会跳过已存在预测文件的视频,打印 Video ... already analyzed at ...(第 572–574 行);overwrite=True 则重新分析,并在 auto_track=True 时同时重新生成已有 tracklet 文件。

六、多动物项目的跟踪与拼接

以下参数仅对多动物项目有意义(compat 层 docstring 的 Note 部分明确列出):

  • auto_track
  • identity_only
  • calibrate
  • n_tracks
  • animal_names

默认情况下 auto_track=True:跟踪(tracking)与拼接(stitching)自动完成,直接产出最终的 .h5 数据文件,行为与单动物项目一致。若 auto_track=False,则必须手动依次运行以下两个子调用才能得到 .h5:

  1. convert_detections2tracklets
  2. stitch_tracklets

关于个体命名与数量:

  • animal_names:希望写入标注数据文件的个体名称列表。若给出且 n_tracks=None,则 n_tracks 自动设为 len(animal_names);若 n_tracks 非空,则必须满足 n_tracks == len(animal_names);若未给出,则从项目 config.yaml 的 individuals 字段加载。
  • n_tracks:默认从 config.yaml 取;当视频中的动物数量与训练时不同时,可传其他值。
  • identity_only=True:当模型已学习个体身份时,组装与跟踪只依赖身份预测。
  • calibrate=True:使用训练数据校准个体组装流程,可提升对错误身体部位连接的鲁棒性,但要求缺失数据极少。

在 TensorFlow 引擎侧,多动物路径会进一步调用 deeplabcut/pose_estimation_tensorflow/predict_multianimal.py 中的相关逻辑,并按 track_method(box/skeleton/ellipse)执行跟踪。

七、TensorFlow 引擎专属参数

  • gputouse:指定 GPU 编号(对照 nvidia-smi 输出的编号);无 GPU 传 None。
  • TFGPUinference=True:用 TensorFlow 代码在 GPU 上执行推理。该能力源自论文 "Pretraining boosts out-of-domain robustness for pose estimation"(Mathis 等,arXiv:1909.11229)。
  • allow_growth=False:某些小显存 GPU 会遇到显存不足问题。设为 True 时显存分配器不再预分配整块 GPU 显存,而是从小的占用开始按需增长。
  • use_openvino="CPU":若 Python 环境装有 OpenVINO,可用它在 CPU 上做推理。

八、PyTorch 引擎的进阶能力

PyTorch 引擎在 deeplabcut/pose_estimation_pytorch/apis/videos.py 中实现,除兼容层透传的参数外,还支持以下专有参数:

  • device:指定推理设备(兼容层会把 gputouse 映射进来)。
  • snapshot_index / detector_snapshot_index:覆盖配置中的姿态模型/检测器快照选择(top-down 模型必须指定检测器快照,否则直接抛 ValueError)。
  • detector_batch_size:检测器推理批大小,默认取 project_cfg.get("detector_batch_size", 1)。
  • top_down_dynamic:top-down 动态裁剪配置,仅用于单动物推理;传入空 dict 使用默认参数(官方不推荐,应针对数据定制)。可用键包括:top_down_crop_size(裁剪缩放尺寸,默认从 pytorch_cfg.yaml 加载)、patch_counts(默认 (3, 2),未找到裁剪时沿宽/高的分块数)、patch_overlap(默认 50,相邻分块重叠像素)、min_bbox_size(默认 (50, 50),最小检测框尺寸)、threshold(默认 0.6,认定个体被检测到的部位得分阈值)、margin(默认 25,关键点生成边界框时的外扩边距)、min_hq_keypoints(默认 2,判定个体被检测并计算 bbox 所需的高分关键点数量)、bbox_from_hq(默认 False,为真时仅用高于阈值的点计算 bbox)。
  • ctd_conditions:仅 CTD(条件 top-down)模型,指定生成条件的 bottom-up 模型;为 None 时从 pytorch_config.yaml 的 "inference": "conditions" 加载,也接受 {"shuffle": 17, "snapshot": "snapshot-best-190.pt"} 形式的 dict。CTD 模型做视频分析必须提供条件(缺失直接抛 ValueError,见第 493–497 行)。
  • ctd_tracking:CTD 模型可直接用于个体跟踪——把第 T 帧的姿态作为第 T+1 帧的条件,此时只有首帧需要 bottom-up 模型初始化;也接受 CTDTrackingConfig 实例。
  • save_as_df:不能与 use_shelve=True 同时使用;在跟踪前把整段视频预测保存为包含 pandas DataFrame 的 .h5。
  • show_gpu_memory:为真时 tqdm 进度条显示当前进程的 GPU 显存占用。
  • inference_cfg:指定 InferenceConfig;为 None 时使用 pytorch_cfg.yaml 中的配置。
  • transform:对视频应用自定义变换(如 albumentations 的 A.Compose)。

九、命令行入口

除了 Python API,还可以通过 CLI 使用该功能。deeplabcut/cli.py 第 383 行定义了 analyze_videos 子命令,最终委托给 deeplabcut.analyze_videos(该 CLI 目前调用的是 deeplabcut.pose_estimation_tensorflow.predict_videos.analyze_videos)。CLI 参数包括:

  • config:项目 config.yaml 完整路径;
  • videos:一个或多个视频路径;
  • -num/--num_shuffles(shuffle):训练数据集 shuffle 索引,默认 1;
  • -vtype/--video_type(video_extensions):输入为目录时的视频扩展名,默认 .avi;
  • -c/--save(save_as_csv):额外保存 .csv,默认关闭。

命令行示例:

python3 dlc.py analyze_videos /home/project/reaching/config.yaml \
    /home/project/reaching/newVideo/1.avi

十、完整可运行示例

以下示例均来自官方 docstring(见 deeplabcut/compat.py 第 724–778 行),可直接复制使用。

在 Windows 上分析单个视频:

deeplabcut.analyze_videos(
    'C:\\myproject\\reaching-task\\config.yaml',
    ['C:\\yourusername\\rig-95\\Videos\\reachingvideo1.avi'],
)

在 Linux/macOS 上分析单个视频:

deeplabcut.analyze_videos(
    '/analysis/project/reaching-task/config.yaml',
    ['/analysis/project/videos/reachingvideo1.avi'],
)

分析目录内所有 .avi 视频:

deeplabcut.analyze_videos(
    '/analysis/project/reaching-task/config.yaml',
    ['/analysis/project/videos'],
    video_extensions='.avi',
)

一次分析多个视频:

deeplabcut.analyze_videos(
    '/analysis/project/reaching-task/config.yaml',
    [
        '/analysis/project/videos/reachingvideo1.avi',
        '/analysis/project/videos/reachingvideo2.avi',
    ],
)

使用 shuffle=2 分析多个视频:

deeplabcut.analyze_videos(
    '/analysis/project/reaching-task/config.yaml',
    [
        '/analysis/project/videos/reachingvideo1.avi',
        '/analysis/project/videos/reachingvideo2.avi',
    ],
    shuffle=2,
)

使用 shuffle=2 并额外保存 CSV:

deeplabcut.analyze_videos(
    '/analysis/project/reaching-task/config.yaml',
    [
        '/analysis/project/videos/reachingvideo1.avi',
        '/analysis/project/videos/reachingvideo2.avi',
    ],
    shuffle=2,
    save_as_csv=True,
)

十一、使用建议与注意事项

  • 输出目录一致性:destfolder 一旦指定,后续的 create_labeled_video、plot_trajectories、filterpredictions 等分析步骤也必须传入同一目录,否则无法定位产物。
  • 多动物手动流程:当 auto_track=False 时,务必记得补跑 convert_detections2tracklets 与 stitch_tracklets,否则只有中间预测文件而没有最终的 .h5。
  • 单动物项目的隐式调整:PyTorch 引擎在单动物项目下会把 save_as_df 强制设为 True,并禁用 use_shelve(打印提示,见 deeplabcut/pose_estimation_pytorch/apis/videos.py 第 462–468 行),以保证单动物输出格式的一致性。
  • 视频损坏处理:若提示"元数据帧数 ≠ 实际处理帧数",说明视频可能损坏,可尝试重新编码视频后再次分析(PyTorch 引擎会在日志中给出对应提示)。
  • 兼容旧代码:3.0.0 之后旧参数名 batchsize、videotype 仍可通过重命名装饰器兼容使用,但建议迁移到新参数名。

通过对兼容层与两个引擎实现的剖析可以看到:analyze_videos 把参数校验、引擎分派、单/多动物流程差异全部收敛在统一入口之下,用户只需关注项目 config.yaml 与上述参数,即可在 TensorFlow 或 PyTorch 引擎上稳定地完成视频姿态推理。

登录后查看全文
DeepLabCut