信息速览
手臂在空气里划过的那条线,肉眼看不到,却几乎支撑了人类所有精细动作的研究:写字、画图、伸手去够一个易拉罐。运动控制领域在过去几十年里反复问同一个问题——这些看起来复杂的轨迹,是不是由少数几个基本单元拼接出来的。一维的伸手动作早就有了相对清晰的答案:速度剖面呈钟形,上升快、下降慢,形态稳定得像模板。可一旦动作变复杂,比如写一个字母、画一朵花,钟形模板就失效了。有人试图在速度矢量的模长上继续找钟形,结果找不出来。CULM 就是在这个僵局里被做出来的。
它的做法换了个角度:不去看速度的总大小,而是把运动拆到三个互相垂直的方向上,分别看内外侧、前后、垂直三段分量。这批数据就是为了支撑这个拆解而采集的——十名健康成年人,十四类画写任务,一套相机式动作捕捉系统,最后只留下三列坐标。文件极简,任务清单却写得极清楚,两者之间的反差本身就是这份数据的性格。
它小得不像一个现代数据集:十个受试者,没有影像,没有标签文件,没有说明文档以外的任何附属物。但正因为小,它把"运动基元是不是可加"这个问题摊开得很干净。一屏速览见下表。
| 维度 | 内容 |
|---|---|
| 全名 | Complex Upper-Limb Movements Database(CULM) |
| 发布方 | PhysioNet(数据来自 Spaulding Rehabilitation Hospital 运动分析实验室) |
| 首次发布 | 2018 年 8 月 30 日,版本 1.0.0 |
| 通讯与提交者 | Paolo Bonato(Harvard Medical School / Spaulding Rehabilitation Hospital) |
| 受试者 | 10 名健康成年人(7 男,3 女,26.4±4.52 岁,9 名右利手) |
| 入选条件 | 无已知影响运动控制的神经或骨科疾病 |
| 任务类别 | 14 类(2 个单词的大写与连笔、6 种几何与理论曲线、1 项抓握、2 项二维伸展、1 项三维随机) |
| 采集设备 | VICON 相机式光学动作捕捉系统(Oxford, UK) |
| 记录对象 | 贴在手上的单个反光标记点 |
| 输出量 | 三维位置(x、y、z),单位米 |
| 文件格式 | CSV,每文件四列:时间、x、y、z |
| 时间单位 | 秒 |
| 采样率 | 官方未公布(时间列可反推) |
| 规模 | 受试者 × 任务的文件组合,具体文件总数官方未在正文列明 |
| 许可 | ODC-BY 1.0,无需注册 |
| 论文 | Scientific Reports 8(1),DOI 10.1038/s41598-018-29470-y |
§1 它要解决的具体麻烦
1.1 当"钟形速度剖面"不再够用
一维点到点运动的速度曲线有一个非常稳定的形状:从静止起步时加速度逐渐增大,到达峰值后再逐渐减小,整体呈钟形,左右不对称。这个形状太稳定了,以至于几十年来它被当作运动基元的原型——大脑似乎只是按不同幅度和时长把这个模板缩放一下,就完成了一次伸手。基于这个假设,研究者建立了大量的加性模型:一个复杂动作等于若干个钟形脉冲的线性叠加。
这个模型在解释一维动作时几乎无可挑剔。问题是,当研究者把同样的思路搬到写字、画图这类复杂上肢动作上时,它崩了。崩的方式很具体:如果把整条手部轨迹的速度矢量取模长,再去找钟形子波,无论怎么调参都拼不出原曲线。有人把这归因于分解算法不够好,有人归因于基元形状不是钟形。CULM 背后的那篇论文选择了第三种解释:问题出在模长这个标量上。模长把三个方向的运动压成了一个数,方向信息在取模那一刻就丢失了,而复杂动作恰恰是靠方向变化组织的。
于是就有了这批数据的设计逻辑:把轨迹按笛卡尔坐标系的三个轴拆开,分别看每个轴上的分量。内外侧方向对应左右摆,前后方向对应推拉,垂直方向对应上下。如果运动基元是沿各轴独立叠加的,那么在每个轴的投影上应该能看到清晰的、形状一致的子波;如果看不到,就说明基元本身是三维的、不能分解。这个判断只能靠同时记录三个方向的原始位置来做,任何只给了速度模长或只给二维投影的数据集都做不到。
1.2 三条常见的错误期待
第一条,期待它是"手部精细动作的通用库"。它记录的只有一个标记点,通常贴在食指或手背上,代表手的整体位置。手指的姿态、腕关节的角度、每一根手指的弯曲程度,全部不在数据里。想拿它做手语识别、装配动作分析、灵巧抓握研究,会立刻撞墙(§2.2)。
第二条,期待它自带"笔画级"或"符号级"标注。文件的组织方式是"一个任务一个文件",没有任何逐点标签告诉你哪一段是抬笔、哪一段落在纸上、哪一段属于哪个字母。字写的是什么,只能从文件名知道;字在文件里的哪一段,需要使用者自己按时间切。这是设计上的省略,不是遗漏。
第三条,期待它能代表运动障碍人群。十个人全部经过筛选,官方明确要求"无已知影响运动控制的神经或骨科疾病"。卒中后的偏瘫手、帕金森病的节律性震颤、共济失调的分解动作,这些恰恰是运动控制研究最想描述的现象,而这份数据一个都没有。
1.3 它能给到的与给不到的
| 你的需求 | 它给的 | 够不够 |
|---|---|---|
| 验证运动基元能否按轴分解 | 同一批动作的三维原始位置,可任意投影到三个轴 | 够,这正是它被采集的目的 |
| 研究书写动作的轨迹生成 | 两个英文单词的大写与连笔版本,同一受试者内可比 | 够做机制演示,不够做字迹识别 |
| 检验理论曲线(频率曲线)的运动学 | 圆、椭圆、三角、花形、螺线、超级云六类参数化图形 | 够,图形定义在文件名里写明 |
| 计划性与非计划性动作对比 | 两组二维伸展任务,有目标与无目标各一 | 够做组内对比 |
| 伸手抓握的路径规划 | 伸向桌面易拉罐的三维动作 | 够,但没有物体位置与抓握时刻标注 |
| 手指与关节层面的运动学 | — | 不够,只有单个标记点 |
| 肌电、脑电或力台数据 | — | 不够,完全没有电生理与力学通道 |
| 运动障碍人群的轨迹 | — | 不够,仅健康受试者 |
| 通用笔迹识别训练 | 两个单词、十个书写者 | 不够,字表极窄 |
| 跨设备或跨中心的泛化验证 | 单一实验室、单一系统 | 不够,只能做自洽性检验 |
1.4 你的处境与它能帮到的事
| 你的处境 | 它能帮你什么 | 下一步该做什么 |
|---|---|---|
| 你在做运动基元的分解算法,需要一批有明确任务语义的三维轨迹 | 十四类任务覆盖书写、绘图、伸展、抓握、随机运动,任务边界由文件名界定 | 先用 §2.3 的读取流程把文件按任务归组,再对每个轴独立做分解,最后合成回三维比较残差 |
| 你在做人机交互或笔迹生成,想找一个最简的轨迹素材 | 纯文本 CSV,无二进制格式、无专有容器,任何语言都能直接读 | 注意坐标系原点与轴向定义官方未写明,先做刚体配准再谈笔画特征 |
| 你在教运动控制课,需要一个"钟形模板失效"的直观例子 | 同一批数据里同时有一维类伸展与复杂曲线,可同图对比 | 计算速度模长与单轴分量的波形对照,用 §4.3 的案例作为讲解顺序 |
| 你在做康复评估的轨迹特征工程 | 提供了健康参照的书写与绘图轨迹形态 | 特征可以借鉴,但人群不匹配,不能直接当常模 |
| 你在评估某个动作捕捉数据集是否值得用来做机制研究 | 任务设计清楚但信息通道极少,正好用来对照"传感器丰富度"与"机制可解释性"的取舍 | 把它与多模态动作数据并列比较,看少了哪些通道会损失哪类结论 |
| 你在核对某篇论文的图表能否复现 | 原始轨迹以米制坐标给出,可重算速度与曲率 | 先确认是否做过滤波,论文与页面都未在正文给出滤波参数 |
1.5 一句话判断
它不是"更大的动作数据集",而是一个把机制问题钉死在三个坐标轴上的实验装置:轨迹短、人少、通道单一,但任务边界清得像实验室记录本,正好够回答"复杂动作能不能拆成沿轴叠加的基元"这一个问题。
1.6 不适合谁:四条边界
不适合拿来做规模训练。 十名受试者、十四类任务,文件组合撑不起深度学习所需的样本多样性。任何以参数量换性能的路线,在这份数据上都会立刻过拟合到个体笔迹习惯。
不适合拿来做临床人群建模。 入选条件是"无已知神经或骨科疾病",这是一份刻意排除病态的数据。用它做异常检测,等于让模型只见过健康样本,却要判出什么叫异常。
不适合拿来做精细手部动作分析。 单标记点方案从物理上就决定了它看不到手指的相对运动。凡是结论涉及"抓握姿态"“指间协调”"捏取力度"的研究,这份数据都无从支撑。
不适合替代原始相机数据做二次重建。 拿到的是厂商软件重建后的结果,重建过程中的标记点补插、平滑与坐标变换都已经发生,且没有随数据给出参数。想回到相机层面重做,必须回到原始采集方。
§2 数据构成与规格
2.1 一次记录由四个数组成
文件是 CSV,没有表头,没有元信息区,没有配套的说明文档。四列的含义在官方页面的 Files 段落里写死了:第一列是时间轴,单位秒;后三列是那个反光标记点的 x、y、z 坐标,单位米。就这四列,别的什么都没有。
这种极简有它的好处。任何语言、任何工具都能直接打开,不需要 WFDB 之类的专用库,不需要解析二进制头文件,不需要处理压缩容器。用 Excel 双击就能看见数值,用 pandas 一行就能读进来。对于一份只服务单一科学问题的数据来说,这是恰当的设计。
| 列序号 | 名称 | 单位 | 取值范围与说明 |
|---|---|---|---|
| 1 | 时间 | 秒 | 从任务开始计,文件内单调递增,起点值官方未公布是否归零 |
| 2 | x | 米 | 内外侧方向(medio-lateral)的位移 |
| 3 | y | 米 | 前后方向(antero-posterior)的位移 |
| 4 | z | 米 | 垂直方向(vertical)的位移 |
表里三个方向的措辞直接来自官方页面对坐标系的描述:轴向分别指向内外侧、前后与垂直。至于 x 究竟对应三者中的哪一个、正向指向哪边,页面没有给出明确的对应关系,需要使用者按运动形态自行判断——比如抓握任务里 z 应当对应垂直方向的抬起与放下。
| 属性 | 值 | 说明 |
|---|---|---|
| 文件编码 | 未在页面声明 | 按纯数值文本处理即可,不含中文与特殊符号 |
| 分隔符 | 逗号 | 官方称为 csv 数据文件 |
| 表头行 | 无 | 四列语义由页面文字给出,不在文件内 |
| 缺失值表示 | 未在页面声明 | 出现缺测时的标记方式需要使用者先检查 |
| 数值精度 | 未在页面声明 | 米制坐标,通常给到毫米以下若干位 |
| 文件命名 | 任务词根 + 受试者区分 | 官方只说明"不同文件对应不同受试者的不同任务" |
| 单文件内容 | 一次任务的连续轨迹 | 是否包含多次重复试次,官方未在正文说明 |
2.2 字段/记录的完整字典
把官方页面里所有能被称为"字段"的东西摊开,其实只有四列加上文件名。但文件名承担的信息量远大于任何一列数值,它编码了任务语义,是这个数据集真正的标签体系。下表把四列与文件名规则合并列出。
| 项 | 类型 | 含义 | 是否逐行变化 | 来源 |
|---|---|---|---|---|
| 时间 | 浮点数 | 秒级时间轴 | 是 | 官方 Files 段 |
| x 坐标 | 浮点数 | 手部标记点内外侧位置,米 | 是 | 官方 Files 段 |
| y 坐标 | 浮点数 | 手部标记点前后位置,米 | 是 | 官方 Files 段 |
| z 坐标 | 浮点数 | 手部标记点垂直位置,米 | 是 | 官方 Files 段 |
| 文件名任务词根 | 字符串 | 十四类任务之一 | 否,按文件 | 官方 Files 段 |
| 文件名受试者标识 | 字符串 | 区分十名受试者 | 否,按文件 | 官方"不同文件名对应不同受试者" |
| 书写内容 | 语义 | Boston 或 Harvard | 否,按文件 | 官方 Files 段 |
| 书写体式 | 语义 | 大写(CA)或连笔(CU) | 否,按文件 | 官方 Files 段 |
| 曲线频率参数 v | 数值 | 0、4/5、4/3、3 四档加无限(圆) | 否,按文件 | 官方 Files 段 |
| 是否有目标 | 布尔 | 计划性为有目标,非计划性为无目标 | 否,按文件 | 官方 Files 段 |
| 空间维度 | 语义 | 二维(纸面)或三维(空间) | 否,按文件 | 官方 Files 段 |
这张表说明了一件事:这份数据的语义全部挂在文件名上,不在数据类型上。x、y、z 三列本身不携带任何任务信息,同样的三列可以是写字母,也可以是画螺线。任何自动化的处理流程,第一步都必须是文件名解析,而不是读数值。
2.3 一条记录的完整解剖
下面这段代码展示从读入到切分为单次动作的最小闭环。它只用标准库加上 pandas 与 numpy,不依赖任何专有接口。代码里的注释按项目约定使用双短横线起头。
#-- 读入一份 CULM 文件并还原为带列名的轨迹表
import re
from pathlib import Path
import numpy as np
import pandas as pd
TASK_HINT = {
"BostonCA": "word_boston_uppercase",
"BostonCU": "word_boston_cursive",
"HarvardCA": "word_harvard_uppercase",
"HarvardCU": "word_harvard_cursive",
"Can": "reach_and_transport_can",
"Circle": "draw_circle",
"Ellipse": "draw_ellipse",
"Flower": "pure_frequency_curve_v_4_3",
"Spiral": "pure_frequency_curve_v_0",
"SuperMegaCloud": "pure_frequency_curve_v_4_5",
"Triangle": "pure_frequency_curve_v_3",
"Planned": "planned_2d_reach",
"Unplanned": "unplanned_2d_reach",
"Randomness": "random_3d_movement",
}
def load_traj(path: Path) -> pd.DataFrame:
#-- 文件无表头,四列依次为时间与三轴坐标
df = pd.read_csv(path, header=None, names=["t", "x", "y", "z"])
name = path.stem
df["task"] = next((v for k, v in TASK_HINT.items() if name.startswith(k)), "unknown")
df["subject"] = re.sub(r"[A-Za-z_]", "", name) or None
df["speed"] = np.r_[np.nan, np.linalg.norm(np.diff(df[["x", "y", "z"]].values, axis=0), axis=1) / np.diff(df["t"].values)]
return df
解剖一条记录时值得注意三个细节。第一,速度不能直接对位置列做简单差分再除以时间步长的平均值,因为时间列可能存在不均匀的采样间隔,必须用逐行的时间差。第二,subject 字段的抽取依赖文件命名规则,而官方页面并没有公布受试者编号的确切格式,上面这段正则只是一个稳健的占位实现,真实文件名需要先人工看几个再调整。第三,速度列第一行必然为空,因为差分的边界效应,这不是数据缺失。
| 解剖步骤 | 输入 | 输出 | 常见坑 |
|---|---|---|---|
| 读取 | CSV 文件 | 四列浮点表 | 误加表头导致首行数据丢失 |
| 命名解析 | 文件名 | 任务类别与受试者标识 | 词根大小写不同,直接字符串相等会漏匹配 |
| 时间校验 | 时间列 | 是否单调、是否等间隔 | 假设等间隔后用固定 dt 差分 |
| 速度计算 | 三轴坐标与时间 | 速度模长与三分量 | 忘记处理首行空值与单位换算 |
| 平滑 | 速度序列 | 去噪后的轨迹 | 平滑窗口乱设,把真实的运动反折抹平 |
| 切分 | 连续轨迹 | 单次试次 | 官方未给试次边界,需按速度过零或停顿切 |
2.4 任务清单与它的设计意图
官方列出的十四类任务是这份数据最值得逐条读的部分,因为它们不是随意拼凑,而是围绕论证主轴排布的。下表按论证角色重新归类,便于理解为什么是这十四类而不是别的。
| 任务词根 | 中文含义 | 空间维度 | 在论证中的角色 | 引用的参数 |
|---|---|---|---|---|
| BostonCA | 大写字母写 Boston | 二维(纸面) | 复杂连续书写,无重复节律 | 无 |
| BostonCU | 连笔写 Boston | 二维(纸面) | 同内容的另一种体式,控制内容变量 | 无 |
| HarvardCA | 大写字母写 Harvard | 二维(纸面) | 换词,检验是否依赖具体字表 | 无 |
| HarvardCU | 连笔写 Harvard | 二维(纸面) | 换词加换体式,双变量控制 | 无 |
| Circle | 画圆 | 二维(纸面) | 周期性运动的基准形态 | v 趋于无穷 |
| Ellipse | 画椭圆 | 二维(纸面) | 各向异性周期运动 | 未给出 |
| Triangle | 画三角形 | 二维(纸面) | 含尖角的非光滑路径 | v=3 |
| Flower | 画花瓣曲线 | 二维(纸面) | 多瓣周期,频率比有理论值 | v=4/3 |
| Spiral | 画螺线 | 二维(纸面) | 半径连续变化的周期运动 | v=0 |
| SuperMegaCloud | 画超级云曲线 | 二维(纸面) | 高频多瓣,最接近"复杂"一端 | v=4/5 |
| Can | 伸向桌面易拉罐并搬运 | 三维 | 真实三维目标导向动作 | 无 |
| Planned | 有目标的二维伸展 | 二维 | 有预知目标 | 无 |
| Unplanned | 无目标的二维伸展 | 二维 | 无预知目标,对比运动规划 | 无 |
| Randomness | 三维随机运动 | 三维 | 去除结构后的对照 | 无 |
"纯频率曲线"这个词在官方描述里反复出现,配合 v 的不同取值,指的是极坐标下半径随角度按某种频率关系变化的闭合或半闭合曲线。v=0 对应螺线,v=3 对应三尖曲线,v=4/3 与 v=4/5 对应不同瓣数的花形。这些参数直接写进了文件名说明,使用者不需要回到论文也能知道每条曲线的几何定义。椭圆是唯一的例外,官方未给出它的参数,因为椭圆的"频率参数"表述不适用。
把这张表竖着读,能看出设计的三层结构。第一层是书写,用两个单词、两种体式形成 2×2 的组合,控制住"写什么"和"怎么写"两个变量。第二层是参数化绘图,用一族理论曲线覆盖从光滑周期到含尖角的各类几何形态,曲线定义有明确数学形式,便于与模型预测直接对照。第三层是伸展与随机,用计划性、非计划性、抓握、随机四类动作把"目标导向"这个变量单独拎出来。三层叠在一起,才使得"基元是否沿轴可加"这个问题能在多种运动类型上反复检验。
2.5 与同类资源的字段差异
动作捕捉类数据集在字段丰富度上差异极大,从单点三维轨迹到全骨架加力学通道都有。把 CULM 放进这个谱系里比较,能最快看清它的位置。
| 资源类型 | 记录对象 | 通道数 | 力学通道 | 标注粒度 | 与 CULM 的差别 |
|---|---|---|---|---|---|
| CULM 这类单点多任务库 | 单个反光标记点 | 3 个坐标 | 无 | 任务级(文件名) | 基准 |
| 全身骨架动作捕捉库 | 数十个标记点 | 数十至上百 | 视配置 | 试次级 | 通道多一个量级,但任务常为行走或体育动作 |
| 多模态康复动作库 | 标记点加肌电或惯性单元 | 十几至几十 | 常有测力台 | 阶段级 | 同时有电生理,可做"神经驱动—运动输出"链路 |
| 笔迹采集板数据 | 笔尖位置与压力 | 2 至 4 | 有压力 | 笔画级 | 在线笔迹专用,采样与笔画切分更成熟 |
| 可穿戴惯性步态库 | 单点或多点加速度 | 3 至 9 | 无 | 事件级 | 传感器便宜,但积分到位置会漂 |
这张表想说的是:CULM 的通道数是整个谱系里的最低一档,比它信息更少的只有纯时间序列。它的价值不在通道,而在任务清单——同一个人在同一场次里完成书写、绘图、伸展、抓握、随机五类动作,这种"一人多任务"的密集设计在动捕类数据里并不常见。骨架库通常是一个人做一类动作做很多次,CULM 反过来,是一个大类做一次。
§3 它是一份关于"手往哪走"的记录
3.1 名字里的 Upper-Limb 指的是路径不是肌群
"上肢运动"这个词在医学语境里容易引起误解,因为它天然让人想到肩、肘、腕的关节链,想到三角肌、肱二头肌这些具体结构。CULM 里的上肢运动指的不是这些,而是手在空间里划过的路径。标记点通常贴在食指近端或手背上,记录的是这个点的位置随时间的变化,其余一切都被略去。
| 你可能以为它能回答 | 它实际能回答 | 缺什么 |
|---|---|---|
| 肩肘关节怎么协同 | 手端点走了什么形状 | 关节角度与骨骼模型 |
| 哪块肌肉在什么时候激活 | 哪个时刻手改变了方向 | 肌电通道 |
| 手指怎么捏住物体 | 手什么时候到达物体附近 | 指尖与物体位置 |
| 动作是否平稳、是否有震颤 | 端点轨迹的平滑度与曲率 | 更高采样率与噪声基准 |
| 动作意图是什么 | 任务类型(由文件名给) | 逐试次的行为标签 |
这张表读下来会有一个清晰的印象:这份数据的全部解释力都集中在运动学末端,也就是"输出的最后一站"。它把问题简化到只问"手怎么走",而不问"手为什么这么走"。对于运动基元这类研究,这种简化是优点——研究者想把机制争论集中在轨迹层面,不想被关节冗余或肌肉共激活干扰。对于应用型研究,这种简化就是硬约束。
3.2 三个方向的坐标为什么是核心
官方在背景段落里把方法论讲得很直接:以往的研究分析速度矢量的模长,失败了;本研究改按笛卡尔坐标系拆分,坐标轴分别指向内外侧、前后、垂直方向。这句话是整份数据的身份说明,它解释了为什么记录必须是三维位置而不是速度或模长。
| 分析对象 | 保有什么 | 丢掉什么 | 能否支撑基元分解 |
|---|---|---|---|
| 速度模长(标量) | 快慢节奏 | 方向变化的全部信息 | 不能,正是此前失败的做法 |
| 速度矢量(三维) | 方向与快慢 | 绝对位置 | 可以,但需要先微分再积分,噪声放大 |
| 三维位置(原始) | 全部运动学信息 | 力与肌肉状态 | 可以,是保留度最高的一层 |
| 二维投影 | 两轴信息 | 第三轴分量 | 只能做部分分解 |
保留原始位置而不是先做微分,是这份数据在信息论上最聪明的选择。位置是积分量,噪声相对温和;速度要经过差分,噪声被步长放大;加速度再差一次,噪声通常已经压过信号。给了位置,使用者可以在任何一步停下来,用自己认为合适的滤波强度做微分;如果只给速度,想回到位置就得积分,误差会累积。这个选择把方法学上的自由度还给了使用方。
3.3 书写任务在运动控制研究里的特殊位置
为什么非要在动作库里放写字?因为书写是极少数同时满足三个条件的日常动作:有明确的语义、有稳定的跨试次重复、有高度的个体特异性。写同一个单词,同一个人每次写出来形状相近但不会完全相同,不同人写出来的差异更大。这种"语义稳定而运动可变"的性质,使它成为研究运动规划的理想素材。
| 动作类型 | 语义明确 | 可重复性 | 个体差异 | 是否需要工具 |
|---|---|---|---|---|
| 伸手够物 | 高 | 高 | 低 | 否 |
| 画几何图形 | 中 | 极高 | 低 | 是 |
| 写单词 | 高 | 中 | 高 | 是 |
| 随机运动 | 无 | 无 | — | 否 |
| 抓握搬运 | 高 | 中 | 中 | 是 |
把 CULM 的十四类任务放进这张表的坐标里,会发现它刻意取了两端:一端是重复性极高的几何曲线,另一端是几乎无结构的随机运动,中间夹着个体差异最大的书写和语义最明确的抓握。这种取法在统计上没有"均衡",但在机制论证上很有效——如果同一个基元假设能同时解释最规整的圆和最无序的随机运动,它的说服力就会强得多。
§4 质量、特色与一处值得细看的案例
4.1 质量的正确问法不是"大不大"
评估一份数据集的质量,通常会先问规模。对 CULM 这样的小库,这个问题会得出"很差"的结论,然后讨论就结束了。更有意义的问法是把质量拆成几项互不替代的属性,逐项看它在哪一项上强。
| 质量维度 | CULM 的表现 | 说明 |
|---|---|---|
| 规模 | 弱 | 10 名受试者,14 类任务 |
| 任务设计的结构性 | 强 | 三层结构,变量控制清楚 |
| 格式的可用性 | 强 | 无表头纯文本 CSV,无专用库依赖 |
| 通道完整度 | 弱 | 仅三维位置 |
| 方法学透明 | 中 | 任务与设备写明,采样与滤波参数缺 |
| 人群代表性 | 弱 | 健康、年轻、以右利手为主 |
| 可复现性 | 中 | 数据公开,但试次切分规则未给 |
| 与论文的一致性 | 强 | 任务清单与论文论证一一对应 |
这张表解释了一个常见困惑:为什么一份规模这么小的数据会被 PhysioNet 收录并持续被引用。原因在于它同时占了"任务结构性"和"格式可用性"两项,而这两项恰恰是大规模数据集常缺的——大库往往任务混杂、格式复杂、参数众多。小而清,是它被使用的理由。
4.2 设备与采集现场的已知约束
采集在 Spaulding Rehabilitation Hospital 的运动分析实验室完成,设备是 VICON 的相机式光学动作捕捉系统。这类系统的原理是一组红外相机同时拍摄贴在身体上的反光标记点,由多视角三角化重建出三维位置。它的精度通常在亚毫米级,但有几个固有约束,会直接写进数据的性质里。
| 约束 | 对数据的影响 | 使用者需要注意什么 |
|---|---|---|
| 需多相机视场重叠 | 动作超出视场会丢失标记点 | 大范围三维动作可能有大段缺测 |
| 反光标记点会被遮挡 | 手转向时标记点可能被身体挡住 | 遮挡期通常由软件插值,形成平滑假象 |
| 依赖静态标定 | 坐标系由标定框决定 | 不同场次的坐标系原点与朝向可能不同 |
| 光学干扰 | 反光物或强光会造成伪标记 | 罕见但会产生孤立的跳变点 |
| 重建为批量离线处理 | 数据是后处理结果非实时流 | 无法还原逐帧的原始相机数据 |
这些约束在官方页面上没有逐条列出,是从设备类型可以推出的一般性质。写在这里不是说官方漏了说明,而是提醒使用者:拿到的是重建后的坐标,不是"干净的真值"。标记点被遮挡的时段,坐标要么缺失,要么是软件插补出来的平滑值,两者在数值上很难区分。做曲率或高阶导数分析时,这类时段会把结论带偏。
| 处理步骤 | 常见做法 | 风险 |
|---|---|---|
| 缺测识别 | 找时间列的间隔跳变 | 插补后的值没有标记,无法识别 |
| 平滑 | 低通滤波或样条平滑 | 截止频率依赖采样率,而采样率未公布 |
| 微分 | 差分或 Savitzky-Golay | 窗口长度不当会把运动反折抹平 |
| 坐标对齐 | 减均值或刚体配准 | 原点的物理意义不明,减均值会破坏绝对位置语义 |
| 单位换算 | 米到毫米 | 极易与厘米混淆,产生数量级错误 |
4.3 案例:同一只手写"Boston"与画一朵花
这一节用一个贯穿的案例把上面几节的抽象说法落到具体操作上。取一名受试者的四个文件:BostonCA(大写写 Boston)、BostonCU(连笔写 Boston)、Flower(v=4/3 的纯频率曲线)、Randomness(三维随机运动)。四份文件记录的其实是同一个标记点、同一个实验室、同一个人,差别只在任务。
| 案例对象 | 轨迹的形状特征 | 三轴分量的表现 | 适合检验什么 |
|---|---|---|---|
| BostonCA | 离散笔画,抬笔与落笔交替 | 垂直分量呈阶梯,水平两轴分段推进 | 离散子动作能否按轴分离 |
| BostonCU | 连续笔画,少抬笔 | 垂直分量起伏小,水平两轴连续 | 连续书写是否仍可分解 |
| Flower | 闭合多瓣曲线,周期明确 | 两轴近似正弦,相位差固定 | 周期性运动中基元的叠加规则 |
| Randomness | 无结构三维游走 | 三轴均无周期,幅度随机 | 分解方法在无结构输入上的假阳性 |
这组对照的设计意图是让方法经受四个不同难度的输入:离散、连续、周期、无结构。一个好的基元分解方法应当在离散与连续书写上给出稳定子波,在周期曲线上给出与理论频率一致的成分,而在随机运动上不产生虚假的规整子波。第四项常常被忽略,但它是检验方法是否过拟合的关键——任何分解算法在随机序列上都能凑出看起来合理的子波,只有对照无结构输入才能看出它到底是在发现结构还是在制造结构。
处理这个案例时,一个具体的技术难点是抬笔。BostonCA 里抬笔意味着标记点离开纸面向上移动,垂直分量会出现一段抬升;但这段抬升并不属于"书写"本身,它是笔画之间的过渡。如果直接把整条轨迹送进分解算法,抬笔段会被当作运动的一部分参与分解,得到的基元里会混入过渡动作的成分。官方没有提供抬笔时刻标注,使用者只能靠垂直分量的阈值或速度停顿来自行判断(§2.3 的切分步骤)。这个判断本身就有主观性,会直接影响最终的子波数量与形状。
4.4 数据完整性与版本
PhysioNet 上的版本记录只显示一个版本:1.0.0,发布于 2018 年 8 月 30 日,页面上的更新日志只有一行"New Database Added: CULM"。这意味着自首次提交以来数据本身没有修订过。
| 项目 | 状态 | 影响 |
|---|---|---|
| 版本号 | 仅 1.0.0 | 无历史版本可比,无法追溯早期问题 |
| 发布日期 | 2018 年 8 月 30 日 | 与论文发表同月 |
| 更新日志 | 仅一条"新库加入" | 无勘误记录 |
| 数据文件修订 | 无 | 引用时不必标注小版本 |
| DOI | 10.13026/C24T0M | 可按版本 DOI 稳定引用 |
| 维护方 | MIT Laboratory for Computational Physiology | 与 PhysioNet 整体一致 |
单一版本对使用者的意义是简明的:引用时只需指向 1.0.0,不必担心下载到与论文不一致的版本。代价是任何后来发现的问题都不会有官方修订,只会在使用者的经验帖里流传。
§5 怎么把它取下来、读进来
5.1 取数的三条路径
PhysioNet 的数据获取有三条常见路径,对 CULM 都适用。第一条是浏览器直接下载,适合只取几个文件;第二条是官方提供的命令行工具,适合批量与校验;第三条是直接拼 URL 抓取,适合脚本化流程。
| 路径 | 适用场景 | 是否需要凭证 | 优点 | 缺点 |
|---|---|---|---|---|
| 网页逐文件下载 | 只看一两个任务 | 否 | 直观 | 无法批量 |
| wget 递归抓目录 | 要全部文件 | 否 | 一条命令取全 | 需要网络稳定 |
| 官方命令行工具 | 需要校验和与断点续传 | 否 | 完整性检查完善 | 多一层工具依赖 |
| 直接拼 URL | 已知文件名 | 否 | 最简单 | 文件名规则不全时失效 |
需要提醒的是,访问权限与下载权限可能不一致。项目页面可以正常浏览,但文件目录在某些网络环境下会返回拒绝访问,此时页面正文仍可读,只是文件列表不可见。遇到这种情况,处理方式是换用官方命令行工具,或者换一个网络出口,而不是反复重试同一个目录 URL。
5.2 用 wget 取全量目录
#-- 取全量文件到本地 culm 目录,跳过上级目录索引
wget -r -N -c -np --accept csv \
-P ./culm_root \
https://physionet.org/files/culm/1.0.0/
#-- 统计取到多少个 CSV 文件
find ./culm_root -name "*.csv" | wc -l
#-- 按任务词根分组计数
for k in BostonCA BostonCU HarvardCA HarvardCU Can Circle Ellipse \
Flower Spiral SuperMegaCloud Triangle Planned Unplanned Randomness
do
printf "%-16s %s\n" "$k" "$(find ./culm_root -name "${k}*.csv" | wc -l)"
done
第二段循环是这套流程里最有信息量的一步。官方只说明"不同文件对应不同受试者的不同任务",但没有给出每个任务下有多少个文件。按词根分组计数,能立刻看出哪些任务所有人都做了、哪些任务只有部分人做——这直接决定了后续能做受试者内对比还是只能做组间对比。
5.3 用 Python 批量加载并做基本体检
#-- 批量载入与基本体检:时长、采样间隔、缺测、量程
from pathlib import Path
import numpy as np
import pandas as pd
rows = []
for p in sorted(Path("./culm_root").rglob("*.csv")):
df = pd.read_csv(p, header=None, names=["t", "x", "y", "z"])
if len(df) < 10:
continue
dt = np.diff(df["t"].values)
step = np.linalg.norm(np.diff(df[["x", "y", "z"]].values, axis=0), axis=1)
rows.append({
"file": p.name,
"n_rows": len(df),
"duration_s": df["t"].iloc[-1] - df["t"].iloc[0],
"dt_median": float(np.median(dt)),
"dt_max": float(dt.max()),
"nan_rows": int(df[["t", "x", "y", "z"]].isna().any(axis=1).sum()),
"path_len_m": float(np.nansum(step)),
"span_x": float(df["x"].max() - df["x"].min()),
"span_y": float(df["y"].max() - df["y"].min()),
"span_z": float(df["z"].max() - df["z"].min()),
})
report = pd.DataFrame(rows).sort_values("file")
report.to_csv("culm_healthcheck.csv", index=False)
print(report.head(20).to_string(index=False))
这段代码输出一张逐文件体检表。其中 dt_median 是从时间列反推采样间隔的唯一途径,因为官方未公布采样率。dt_max 远大于 dt_median 时,说明该文件中间有采集中断或标记点丢失;nan_rows 大于零说明存在显式缺测。path_len_m 与三个 span 的比值能大致区分"来回走"与"单程走",对判断任务形态有用。
| 体检字段 | 读法 | 触发的后续动作 |
|---|---|---|
| n_rows | 行数,粗略反映采样点规模 | 行数极少时考虑该文件不可用 |
| duration_s | 任务时长 | 与任务类型对照,书写通常长于几何图形 |
| dt_median | 反推的采样间隔 | 作为后续滤波与差分的基准 |
| dt_max | 最大相邻时间差 | 明显偏大时定位中断区间 |
| nan_rows | 缺测行数 | 大于零时决定插值还是剔除 |
| path_len_m | 轨迹总长 | 用于速度与曲率的归一化 |
| span_x/y/z | 三个方向的活动范围 | 判断动作的空间维度(二维还是三维) |
5.4 用 R 读入并画三轴分量
#-- 用 R 读一份文件,画三个方向的分量与合速度
p <- "./culm_root/BostonCU_01.csv"
d <- read.csv(p, header = FALSE, col.names = c("t", "x", "y", "z"))
d$dt <- c(NA, diff(d$t))
d$vx <- c(NA, diff(d$x)) / d$dt
d$vy <- c(NA, diff(d$y)) / d$dt
d$vz <- c(NA, diff(d$z)) / d$dt
d$v <- sqrt(d$vx^2 + d$vy^2 + d$vz^2)
par(mfrow = c(2, 1), mar = c(4, 4, 2, 1))
matplot(d$t, cbind(d$vx, d$vy, d$vz), type = "l", lty = 1,
xlab = "time (s)", ylab = "velocity component (m/s)")
plot(d$t, d$v, type = "l", xlab = "time (s)", ylab = "speed (m/s)")
上半张图是三轴分量的叠加,下半张图是合速度。把它们对照着看,就是这份数据最想让人看到的画面:合速度可能是一个平滑的钟形,但三个分量各自形状完全不同,甚至在合速度接近零的时刻,某一个分量正处于峰值。这正是"看模长会丢信息"的直观证明。
5.5 按受试者与任务做交叉索引
#-- 建立 受试者 x 任务 的可用性矩阵,避免误把缺失当成缺失值
import re
import pandas as pd
from pathlib import Path
TASKS = ["BostonCA", "BostonCU", "HarvardCA", "HarvardCU", "Can", "Circle",
"Ellipse", "Flower", "Spiral", "SuperMegaCloud", "Triangle",
"Planned", "Unplanned", "Randomness"]
recs = []
for p in Path("./culm_root").rglob("*.csv"):
name = p.stem
task = next((t for t in TASKS if t in name), None)
subj = re.sub("|".join(TASKS), "", name).strip("_- ")
recs.append({"subject": subj or "unknown", "task": task, "file": p.name})
idx = pd.DataFrame(recs)
matrix = idx.pivot_table(index="subject", columns="task",
values="file", aggfunc="count").fillna(0).astype(int)
matrix.to_csv("culm_coverage.csv")
print(matrix)
这张矩阵表的作用是把"文件不存在"与"文件存在但内容缺失"分开。如果某个受试者某任务在矩阵里是 0,说明他没有做这项任务,此时在训练与评估时都应当整体跳过,而不是用一个空表去填充,后者会在统计时把该受试者的可选项中位数拉低。
5.6 常见取数故障与处置
| 现象 | 可能原因 | 处置方式 |
|---|---|---|
| 目录 URL 返回 403 | 网络出口被限或地区策略 | 改用官方工具或换网络出口,页面正文仍可读 |
| 下载到的 CSV 首行被当成表头 | 工具自动推断表头 | 强制 header=None 或 header=FALSE |
| 时间列非单调 | 拼接多个文件或排序错误 | 逐文件处理,不要先合并再排序 |
| 速度出现孤立极大值 | 标记点跳变或重建伪影 | 用中值滤波粗筛,标记该帧而非直接删 |
| 三轴顺序与预期不符 | 坐标系定义未在页面写明 | 用抓握任务的垂直抬升反推哪一轴是垂直 |
| 不同文件时间起点不同 | 每文件独立计时 | 需要在跨文件比较时先做时间对齐 |
§6 与库内条目的关系
6.1 关系图谱
千方医数集的口径下,与 CULM 相邻的条目可以分成三圈。第一圈是同为光学动作捕捉的资源,第二圈是同一机构或同一问题域的资源,第三圈是外围的可穿戴与步态资源。
| 圈层 | 库内条目 | 与 CULM 的共同点 | 与 CULM 的分野 |
|---|---|---|---|
| 内核:光学动捕 | ACL Jump-Landing MoCap | 同为相机式标记点动捕,同为健康受试者小样本 | 该条目是下肢跳跃落地加测力台,CULM 是上肢手部轨迹 |
| 内核:运动学与力学 | The OpenBiomechanics Project | 同为自有采集的高精度运动学数据 | 该条目规模大、面向运动表现,CULM 面向机制论证 |
| 中圈:康复动作 | UL-RED 康复运动数据集 | 同为上肢动作任务 | 该条目是康复操成套动作,任务由运动处方定义,CULM 由实验问题定义 |
| 中圈:康复可穿戴 | REHAB 卒中可穿戴运动学 | 同为上肢功能相关的运动记录 | 该条目是卒中人群加惯性传感器,CULM 是健康人群加光学定位 |
| 外圈:步态与神经 | 帕金森病步态库、神经退行性步态库 | 都关心运动的病理改变 | 那些是临床人群步态,与 CULM 的健康上肢轨迹几乎不重叠 |
| 外圈:儿科步态 | LIVE-GaitNeuroKids | 同为纵向或多模态设计 | 该条目是多模态加儿科,与 CULM 的单通道成人设计相反 |
这张图的价值是给检索者一个明确的定位:想找"上肢、健康人、光学动捕、任务设计清楚"的组合,库内目前只有 CULM 一个;想找"上肢加临床人群加多模态",应当看 REHAB 那条。
6.2 检索路径
按需求反查时的检索路径大致有这几条,每条都对应一个不同的入口词。
| 你的检索词 | 会命中的条目 | 命中后如何判断是不是你要的 |
|---|---|---|
| 动作捕捉 / motion capture | ACL Jump-Landing、OpenBiomechanics、CULM | 看记录的是上肢还是下肢,是否有力学通道 |
| 上肢运动 / upper limb | CULM、UL-RED、REHAB | 看人群是健康还是康复,看通道数 |
| 运动基元 / motor primitives | CULM | 目前只有它会以基元分解为主轴 |
| 书写 / handwriting | CULM | 库内笔迹类条目极少,命中范围很窄 |
| 康复评估 | UL-RED、REHAB、CULM | 只有 CULM 不涉及康复人群,评估用途需谨慎 |
| 惯性 / IMU | REHAB、步态类条目 | CULM 不含惯性传感器,命中即为误配 |
检索时最省事的判据是通道数。CULM 只有三维坐标三列,看到列数远多于四、或者有肌电与测力通道的,基本可以确定不是它。
§7 质量评估与局限性
7.0 阅读本节前的一个前置校正
在讨论局限之前需要先纠正一个常见的错位:很多人拿"数据量"这一把尺子去量所有数据集,量出 CULM 很薄,然后得出结论说它质量差。这个判断是误判,因为它把"为机制论证而采集"和"为模型训练而采集"混成了一种东西。
| 采集目的 | 优化目标 | 规模是否重要 | 通道是否重要 | 典型的失败模式 |
|---|---|---|---|---|
| 训练通用模型 | 覆盖度与多样性 | 极重要 | 重要 | 样本少导致过拟合 |
| 验证机制假设 | 变量控制与可解释性 | 次要 | 够用即可 | 设计混淆导致结论不可归因 |
| 建立临床常模 | 人群代表性 | 极重要 | 视指标 | 人群偏倚导致常模失真 |
| 做方法学对照 | 格式清晰与可复现 | 次要 | 次要 | 参数缺失导致无法复现 |
CULM 明确属于第二类。它的十个人不是抽样抽出来的,是为了一场受控实验招来的;它的十四类任务不是为了覆盖什么分布,是为了把三个变量(内容、形态、目标)各自切开。用第一类的尺子去量它,结论必然是错的。下面的评分表按第二类的口径给出。
7.1 五维评分
按 DAIMS 的常用维度打分,每项 1–5 分,分数针对"作为运动控制机制研究数据"这个用途:
| 维度 | 评分 | 依据 | 扣分点 |
|---|---|---|---|
| 规模与覆盖 | 2/5 | 10 名受试者,14 类任务 | 无任何人群多样性而言 |
| 结构清晰度 | 4/5 | 四列纯文本,任务由文件名界定 | 受试者编号格式未公布 |
| 方法学透明 | 3/5 | 设备、机构、任务与论文都写明 | 采样率、滤波、坐标系与试次规则缺 |
| 可复现性 | 3/5 | 数据全公开、无版本变动 | 试次切分与预处理参数需自定 |
| 科学针对性 | 5/5 | 任务设计与论文论证一一对应 | 几乎无可挑剔 |
| 加权总评 | 3.4/5 | 面向机制研究很高,面向训练很低 | 用途错配是主要风险 |
这张表不宜直接理解成"3.4 分的中等数据集"。更准确的读法是:它在针对性这一项拿满,在规模这一项拿到底,中间三项取决于你要做什么。如果你的问题正是它设计来解决的那个,它是 5 分;如果你的问题是训练一个笔迹模型,它是 1 分。
7.2 与论文的关系有多紧
这份数据与论文的绑定程度非常高。任务清单里每一类都对应论文论证的一个环节,文件名里的参数(v 取值、CA/CU、Planned/Unplanned)也直接来自论文的实验设计。这意味着脱离论文单独看数据,会损失相当一部分信息。
| 信息 | 是否在数据包内 | 是否在页面正文 | 是否只在论文里 |
|---|---|---|---|
| 任务名称与含义 | 部分(文件名) | 是 | 否 |
| 任务执行的具体指令 | 否 | 否 | 是 |
| 每任务的重复次数 | 否 | 否 | 是 |
| 标记点贴附位置 | 否 | 否(只说"代表手部轨迹") | 是 |
| 采样率与滤波 | 否 | 否 | 视论文方法段 |
| 分析方法的完整步骤 | 否 | 否 | 是 |
最后一行值得强调。官方页面的背景段把方法论的核心思路说清楚了——不看模长,改看三轴分量——但没有给出具体的分解算法与参数。想完整复现论文结果,必须在数据之外把论文的方法段也读透。这不是缺陷,是数据包的边界;只是使用者容易误以为"有数据就能复现"。
7.3 已知的、可枚举的偏差
| 偏差 | 方向 | 对结论的影响 | 可缓解的做法 |
|---|---|---|---|
| 样本量极小 | 10 人 | 个体差异会主导组间比较 | 以受试者为重复测量单元,做受试者内对比 |
| 利手不平衡 | 9 右 1 左 | 利手效应无法独立估计 | 不做利手相关结论,或明确声明无法估计 |
| 年龄集中在青年 | 26.4±4.52 岁 | 无法外推到老年与儿童 | 结论限定为青年成人 |
| 健康筛选严格 | 排除神经与骨科疾病 | 无法描述病理轨迹 | 不用于异常检测的阳性类 |
| 单实验室单设备 | 一家医院一个系统 | 跨设备泛化未验证 | 结论限定在该采集条件 |
| 单标记点 | 无关节信息 | 无法探讨关节冗余与协调 | 只做末端运动学结论 |
| 任务指令缺失 | 复现依赖论文 | 试次边界有主观性 | 明确写出自己的切分规则 |
其中利手这一项容易被忽略。官方给了"9 名右利手"这个数字,意味着只有 1 名左利手。任何想在 CULM 上比较左右手书写差异的研究,都会因为左利手样本只有一人而无法成立。这不是数据的问题,是设计时的取样现实,但使用者在提出假设时应当先看到这一点。
7.4 外部验证矩阵
一份小样本数据集的可信度,很大程度上取决于它是否被外部独立工作复用过。下表列出可核实的验证层面。
| 验证层面 | 状态 | 说明 |
|---|---|---|
| 官方内部一致性 | 已确认 | 任务清单与论文论证对应齐整 |
| 独立复现论文结果 | 未核实 | 需要逐篇检索引用文献,本文未做 |
| 跨中心再采集 | 官方未公布 | 未见同协议的第二中心数据 |
| 与其他动捕库的交叉校验 | 未核实 | 任务设计差异大,难以直接对齐 |
| 长期维护状态 | 已确认 | 仅 1.0.0,无后续修订 |
| 社区使用规模 | 未核实 | 页面显示的项目浏览量为单一时刻快照,不宜当引用量 |
这张表里多数项是"未核实"或"官方未公布",这不是敷衍,而是诚实的边界。以本次调研的时间预算,只足够核实官方页面与论文索引信息,不足以做完整的引用网络分析。凡是标"未核实"的地方,使用者应当自己去查,而不是把这里的空白当成"不存在"。
7.5 它为何能持续:一个未被更好替代的实验设计
一份 2018 年的小数据,在动捕库越做越大的今天仍然被下载,原因不在于它提供了什么别处没有的数据量,而在于它提供了一种别处少见的实验设计:同一个人,同一场次,用同一台设备,把书写、绘图、伸展、抓握、随机五类动作连续做完。这种"一人多任务"的密集设计,是后来那些追求规模的数据集主动放弃的——大库要么横向扩人,要么纵向加通道,很少再有人愿意为了控制变量而牺牲样本量。CULM 正好站在这个取舍的另一端,于是它成了一件难以被规模替代的参照物。
§8 生态位与历史
8.1 从钟形脉冲到三轴分解的历史沿革
要理解 CULM 的位置,需要把它放进运动基元研究的一条长线里看。这条线大致可以分为四段。
| 阶段 | 主要主张 | 代表性问题 | 与 CULM 的关系 |
|---|---|---|---|
| 早期:钟形模板 | 一维伸手的速度剖面稳定呈钟形 | 模板是否普适 | CULM 的对照组,正是它失效的地方 |
| 中期:模长叠加 | 复杂动作等于若干钟形脉冲在模长上叠加 | 能否用模长分解复杂动作 | 官方背景段明确指出此路失败 |
| 转折:方向丢失 | 取模长丢失了方向信息 | 应当换一种分解对象 | CULM 采集的直接动因 |
| CULM 阶段:按轴分解 | 在笛卡尔三轴上分别寻找基元 | 基元是否沿轴独立可加 | 本研究的主张 |
这条线说明 CULM 不是凭空出现的新库,而是一次方法学转向的产物。它的价值在于把"换一种分解对象"这个主张变成了可被检验的数据:如果后来者有更好的分解方法,可以回到同一批轨迹上重新做,结论是否成立一目了然。
8.2 它在 PhysioNet 里的位置
PhysioNet 的主体是生理信号与临床数据,心电、脑电、呼吸、影像占绝大多数。运动轨迹类数据在库内的比例很小,CULM 属于少数派。
| 类别 | 在 PhysioNet 的占比(定性) | 典型库 | CULM 的归属 |
|---|---|---|---|
| 心电与心律 | 多数 | MIT-BIH 系列、INCART | 否 |
| 脑电与睡眠 | 较多 | 睡眠分期、癫痫相关库 | 否 |
| 影像与形态 | 较少 | 各类影像挑战数据 | 否 |
| 运动与步态 | 少数 | 步态相关库、CULM | 是 |
| 呼吸与力学 | 少数 | 各类波形库 | 否 |
这种少数派位置有两个后果。好处是同类竞品少,检索"手部轨迹"时几乎没有干扰;坏处是它很难享受到心电类数据那种成熟的工具生态——没有专门的读取库,没有统一的注释格式,也没有现成的基准划分。
8.3 机构与作者线索
数据的提交者是 Paolo Bonato,隶属 Harvard Medical School 与 Spaulding Rehabilitation Hospital,采集地点在后者院内的运动分析实验室。论文作者名单横跨多个机构,通讯信息在页面上给出了两位联系人。这些线索的实际用途是判断数据来源的可信度与联系途径。
| 线索 | 内容 | 用途 |
|---|---|---|
| 提交者 | Paolo Bonato | 判断机构背景与后续维护方 |
| 机构 | Harvard Medical School / Spaulding Rehabilitation Hospital | 波士顿的康复工程重镇 |
| 实验室 | Motion Analysis Lab | 采集现场,设备与协议由其掌握 |
| 联系人 | 页面给出两位,含论文第一作者 | 追问问卷或协议细节的唯一渠道 |
| 伦理 | 经 Spaulding 的机构审查委员会批准 | 引用时的伦理声明依据 |
| 知情同意 | 全部受试者书面同意 | 数据可公开的前提 |
需要留意的是,联系人的邮箱在页面上是明文,但回复并不保证。若有必须澄清的问题(比如采样率),更稳妥的做法是先查论文方法段,再考虑联系。
8.4 从发表到被引用的路径
2018 年 8 月 30 日,PhysioNet 更新日志出现一行"New Database Added: CULM",同日版本 1.0.0 上线。论文发表在 Scientific Reports 同年的第 8 卷。此后没有版本更新。
| 时间 | 事件 | 可核实性 |
|---|---|---|
| 2018 年(论文) | Scientific Reports 8(1) 发表 | 页面引用信息确认 |
| 2018 年 8 月 30 日 | PhysioNet 1.0.0 上线 | 页面更新日志确认 |
| 2018 年以后 | 无版本修订 | 版本列表确认 |
| 2026 年 | 页面仍可访问,正文未改 | 本次访问确认 |
这条时间线非常简单,简单到几乎没有什么可讲的。但对使用者有意义的一点是:页码上的任何描述都不会随时间漂移。2018 年写的任务清单,2026 年读还是同一份。这在长尾数据的引用里是一种被低估的优点。
§9 使用指引
9.1 三种角色的路径
不同角色拿到这份数据,最短的可用路径完全不同。
| 角色 | 首要目标 | 建议第一步 | 建议第二步 | 常见误区 |
|---|---|---|---|---|
| 运动控制研究者 | 检验基元假设 | 完整读论文方法段 | 复现三轴分解,比对残差 | 直接套用别人的分解参数 |
| 算法工程师 | 找一个干净的轨迹样例 | 读 §2.3 的加载代码 | 先做体检表,再决定清洗策略 | 假设采样率固定 |
| 教学与科普 | 讲清"模长丢信息" | 取一份书写文件 | 合速度与三轴分量同图对照 | 用几何图形代替书写做示例 |
| 康复评估研究者 | 借鉴轨迹特征 | 明确声明人群不匹配 | 把特征当作描述量而非常模 | 直接拿十人当健康常模 |
对研究者来说,第一步永远是读论文而不是读数据。数据里的四列不会告诉你标记点贴在哪、任务怎么下的指令、试次怎么组织的,这些只在论文里。对工程师来说,反过来,先跑通加载再回去读方法,效率更高。对教学来说,最有说服力的例子是书写任务,因为它的三轴分量差异最直观。
9.2 一条最短的可用流程
#-- 最短可用流程:取一个文件,做体检,画三轴分量
set -e
mkdir -p culm_demo && cd culm_demo
#-- 用官方目录取单个任务的全部文件
wget -r -N -c -np --accept "BostonCU*.csv" \
https://physionet.org/files/culm/1.0.0/ || echo "目录受限,改用逐文件 URL"
#-- 选第一个文件做快速体检
FIRST=$(find . -name "BostonCU*.csv" | head -n 1)
python3 - "$FIRST" <<'PY'
import sys
import numpy as np
import pandas as pd
df = pd.read_csv(sys.argv[1], header=None, names=["t", "x", "y", "z"])
dt = np.diff(df["t"].values)
d = np.diff(df[["x", "y", "z"]].values, axis=0)
v = np.linalg.norm(d, axis=1) / dt
print("rows :", len(df))
print("duration (s):", round(df["t"].iloc[-1] - df["t"].iloc[0], 3))
print("dt median :", round(float(np.median(dt)), 5))
print("speed mean :", round(float(np.nanmean(v)), 4), "m/s")
print("path length :", round(float(np.nansum(np.linalg.norm(d, axis=1))), 4), "m")
PY
这段脚本的四行打印,就是判断一个文件是否可用的最小信息集:行数决定统计是否稳定,时长决定任务是否完整,采样间隔决定后续滤波参数,路径长度与速度均值决定这像不像真实的手部运动。四行都对得上,再进下一步。
9.3 引用方式
引用这份数据需要两份文献,一份是数据集本身,一份是 PhysioNet 平台。官方页面给出了数据集的标准引用与 BibTeX 入口。
| 引用对象 | 建议写法 | 关键要素 |
|---|---|---|
| 数据集(首选) | 按页面给出的作者列表与年份,引用 Scientific Reports 论文并注明数据来自 PhysioNet | 作者、年份、期刊、卷期、DOI |
| 数据集 DOI | 10.13026/C24T0M | 指向 1.0.0 版本 |
| PhysioNet 平台 | 按平台给出的标准引用 | 平台论文与访问日期 |
| 许可署名 | 注明 ODC-BY 1.0 与是否修改 | 修改说明写清楚做了哪些变换 |
实际写作时最容易漏的是"是否修改"。只要你做过滤波、重采样、坐标变换或文件重组,就应当在引用处写明,这是 ODC-BY 的署名义务的一部分,也是别人能否复现你的关键。
§10 AI 使用声明
| 项目 | 说明 |
|---|---|
| 数据性质 | 全部为人类受试者的运动学轨迹,不含影像与文本 |
| 受试者信息 | 页面仅给出性别、年龄、利手与人数,无姓名、无日期、无地点 |
| 伦理依据 | 经 Spaulding Rehabilitation Hospital 机构审查委员会批准,全部受试者书面知情同意 |
| 是否可用于训练模型 | 许可允许,但样本量决定它不适合作为主训练集 |
| 已知的模型风险 | 十人数据训练出的轨迹生成模型会强烈拟合个体笔迹习惯 |
| 再识别风险 | 官方未公布评估;轨迹本身不含身份信息,但极小的受试者集合带有情境可识别性 |
| 适合的 AI 应用 | 机制检验、轨迹生成方法的对照实验、教学示例 |
| 不适合的 AI 应用 | 临床诊断辅助、人群级常模、通用笔迹识别 |
这份数据在 AI 伦理上的争议点很少,因为它既不含影像也不含文本,个人信息的暴露面仅限于几个人口学数字。真正需要使用者自己把关的是用途:拿十个人去训练一个宣称"通用"的运动生成模型,问题不在伦理而在方法。
常见误读(避坑清单)
| 说法 | 实际 | 证据 |
|---|---|---|
| 这是一个手部肌电数据集 | 只有三维坐标,无电生理通道 | 官方 Files 段写的是四列时间与坐标 |
| 每个受试者都做了全部十四类任务 | 官方未声明完整交叉,需按文件核对 | 页面只说"不同文件对应不同受试者的不同任务" |
| 采样率是某个固定值(如 100 Hz) | 官方未公布 | 正文无采样率数值,需从时间列反推 |
| 数据已经被滤波过,可以直接算加速度 | 滤波情况未说明 | 页面无预处理参数,厂商软件的重建细节未公开 |
| 它能识别手写的字母 | 只有两个单词、十个书写者 | 任务清单只有 Boston 与 Harvard |
| 它适合做卒中后运动评估的基准 | 受试者明确排除神经疾病 | 入选条件为无已知神经或骨科疾病 |
| 它是下肢或全身动作数据 | 记录的是手部单个标记点 | 官方称"代表手部轨迹"的反光标记点 |
| 文件名里的 v=4/3 是速度 | 是纯频率曲线的频率参数 | 官方 Files 段对 Flower 等曲目的说明 |
| 版本更新过,可能有勘误 | 仅 1.0.0,无修订记录 | 版本列表只有一个版本 |
| 十个人足够做群体统计推断 | 样本量过小,个体差异主导 | 官方给出的受试者人数为十 |
FAQ
问:CULM 和一般的动作捕捉数据集有什么区别?
答:最大的区别在任务设计。一般动捕库会为同一类动作采集大量重复,追求覆盖度;CULM 是同一批人做十四类不同任务,追求变量控制。它更适合问"动作是怎么组织的",不太适合问"这个动作能识别得多准"。
问:只有三维坐标,为什么还被认为信息足够?
答:因为它的科学问题是关于轨迹本身的。运动基元的争论发生在末端轨迹层面,关节与肌肉是更下一层的解释。对这个问题,末端三轴位置恰好是既充分又不冗余的那一层。
问:时间列能反推采样率吗?
答:能。取相邻时间差的中位数就是采样间隔的倒数。但这是使用者的推断,不是官方给出的规格。写进论文时应当说明"由时间列推得",不要写成官方参数。
问:为什么同一任务的文件名里要区分 CA 与 CU?
答:CA 是大写(capital letters),CU 是连笔(cursive)。区别在于书写时抬笔的次数:大写字母逐字母断开,连笔则尽量连贯。这个区分把"内容"控制住,单独变化"体式",是实验设计的一部分。
问:Planned 与 Unplanned 到底差在哪?
答:差在有没有预知目标。计划性动作的目标位置事先知道,运动可以先规划再执行;非计划性动作的目标事先不知道,运动要在过程中调整。这两类放在一起,才能看运动规划对轨迹形态的影响。
问:抓握任务里有物体位置的标注吗?
答:官方未公布。页面只说这是伸向桌上易拉罐并搬运的三维动作,没有给出易拉罐的位置坐标或抓握时刻。需要用轨迹本身的停顿与速度变化去推断。
问:能做左右手对比吗?
答:从理论上可以,从样本上不行。十名受试者里九名右利手,左利手只有一人,任何左右对比的结果都会被这一个人的个体特征决定。
问:想用它做笔迹识别的预训练,可行吗?
答:可以做探索,但收益有限。只有两个单词、十个书写者,字表与书写者的多样性都不足以支撑通用识别。更现实的用法是把它当作轨迹生成或表示学习的辅助素材。
问:文件里第一行是表头吗?
答:不是。官方描述为"第一个数据列是时间轴",四个列都是数据。用 pandas 读取时务必设 header=None,否则首个采样点会被当成列名吞掉。
问:数据需要注册才能下载吗?
答:不需要。访问政策写明任何人只要遵守许可条款即可访问。页面本身无需登录,只是某些网络环境下文件目录可能返回拒绝访问。
问:可以商用吗?
答:可以。ODC-BY 1.0 允许商业使用,条件是署名与说明修改情况。引用处需要写明数据来源、作者与许可名称。
问:为什么它在 PhysioNet 上而不是在专门的动作库上?
答:PhysioNet 收录标准看重的是数据对生物医学研究的可复用性,而非数据模态。这份数据虽然是小众的运动轨迹,但有明确的科学问题、清晰的格式与完整的伦理说明,符合收录标准。
术语表
| 术语 | 含义 |
|---|---|
| CULM | Complex Upper-Limb Movements,复杂上肢运动数据库 |
| 运动基元 | motor primitive,被假设为构成复杂动作的基本运动单元 |
| 钟形速度剖面 | 一维点到点运动中速度随时间呈钟形的典型形态 |
| 速度矢量模长 | 三轴速度分量的欧氏范数,即合速度 |
| 笛卡尔坐标系 | 用三个互相垂直的轴描述空间位置的坐标系 |
| 内外侧方向 | medio-lateral,身体的左右方向 |
| 前后方向 | antero-posterior,身体的前后方向 |
| 垂直方向 | vertical,重力反方向 |
| 反光标记点 | retroreflective marker,贴在体表供相机识别的被动标记 |
| 光学动作捕捉 | 用多台相机三角化重建标记点三维位置的技术 |
| VICON | 英国牛津的动作捕捉系统厂商 |
| 上升时间 | 速度从零升到峰值所用的时间 |
| 纯频率曲线 | 极坐标下半径按频率参数变化得到的一族曲线 |
| 频率参数 v | 描述曲线瓣数与形状的无量纲参数 |
| 书写体式 | 大写或连笔,对应抬笔频率的差异 |
| 计划性动作 | planned,目标位置事先已知的伸展动作 |
| 非计划性动作 | unplanned,目标位置事先未知的伸展动作 |
| 三维随机运动 | 无目标、无结构的空间游走动作 |
| 试次 | trial,一次完整执行的任务单元 |
| 抬笔 | 书写中笔离开纸面的过渡阶段 |
| 遮档 | 标记点被身体或物体遮挡导致相机不可见 |
| 重建 | 由多视角二维图像计算三维坐标的过程 |
| 标定 | 确定相机内外参数与坐标系的过程 |
| 采样间隔 | 相邻采样时刻之间的时间差 |
| 缺测 | 标记点在某帧未被成功识别而导致的数据空缺 |
| ODC-BY | Open Data Commons Attribution,开放数据署名许可 |
| DOI | 数字对象标识符,用于稳定引用 |
附录 A:核心数字核对表
| 项 | 值 | 来源 | 来源层级 |
|---|---|---|---|
| 受试者人数 | 10 | 官方页面 Background 段 | 官方 |
| 男性人数 | 7 | 官方页面 Background 段 | 官方 |
| 年龄 | 26.4±4.52 岁 | 官方页面 Background 段 | 官方 |
| 右利手人数 | 9 | 官方页面 Background 段 | 官方 |
| 任务类别数 | 14 | 官方页面 Files 段逐条统计 | 官方 |
| 设备厂商 | VICON, Oxford UK | 官方页面 Data Collection 段 | 官方 |
| 单位 | 米 | 官方页面 Files 段 | 官方 |
| 列数 | 4 | 官方页面 Files 段 | 官方 |
| 采样率 | 未公布 | 官方页面无此数值 | 官方未公布 |
| 滤波参数 | 未公布 | 官方页面无此数值 | 官方未公布 |
| 坐标系原点 | 未公布 | 官方页面无此数值 | 官方未公布 |
| 文件数量 | 未公布总量 | 官方页面未列文件清单 | 官方未公布 |
| 许可 | ODC-BY 1.0 | 官方页面 License 段 | 官方 |
| 版本号 | 1.0.0 | 官方页面版本区 | 官方 |
| 发布日期 | 2018-08-30 | 官方页面更新日志 | 官方 |
| DOI | 10.13026/C24T0M | 官方页面 DOI 段 | 官方 |
| 论文 DOI | 10.1038/s41598-018-29470-y | 官方页面引用段 | 官方 |
| 机构审查 | Spaulding 机构审查委员会 | 官方页面 Background 段 | 官方 |
附录 B:数字的来源分层
| 层级 | 数字 | 说明 |
|---|---|---|
| 官方页面正文 | 10 人、7 男、26.4±4.52 岁、9 右利手、14 类任务、米制、四列、VICON、ODC-BY 1.0、1.0.0、2018-08-30、两个 DOI | 可直接引用,无需二次核实 |
| 论文摘要与索引信息 | 期刊名、卷期、DOI、作者列表、机构归属 | 页面引用段已给全,可直接引用 |
| 由设备类型推断 | 相机三角化原理、遮挡导致缺测、插值会造成平滑假象 | 一般工程常识,非本数据专属声明 |
| 由数据自算可得但本次未做 | 采样率、文件总数、每任务文件数、轨迹时长 | 需下载全量后才能得到 |
| 未核实 | 独立复现情况、引用规模、跨中心验证 | 本次调研未覆盖 |
| 官方未公布 | 采样率数值、滤波参数、坐标系原点、试次次数、标记点贴附位置 | 只能通过论文或联系作者获得 |
附录 C:完整参考文献
| 序号 | 文献 | 用途 |
|---|---|---|
| 1 | Miranda JGV, Daneault JF, Vergara-Diaz G, 等. Complex Upper-Limb Movements Are Generated by Combining Motor Primitives that Scale with the Movement Size. Scientific Reports. 2018;8(1). DOI:10.1038/s41598-018-29470-y | 数据集配套论文,方法学与结论的唯一完整出处 |
| 2 | PhysioNet 项目页:Complex Upper-Limb Movements v1.0.0,https://physionet.org/content/culm/1.0.0/ | 数据集官方说明,本页多数事实的来源 |
| 3 | PhysioNet 平台标准引用(平台页面给出) | 平台层面的署名要求 |
| 4 | Open Data Commons Attribution License v1.0 文本 | 许可条款原文 |
| 5 | Spaulding Rehabilitation Hospital 运动分析实验室页面 | 采集现场背景 |
附录 D:任务分组代码
#-- 按论证角色给任务打标签,便于分组统计与对照实验
GROUPS = {
"writing": ["BostonCA", "BostonCU", "HarvardCA", "HarvardCU"],
"geometry": ["Circle", "Ellipse", "Triangle", "Flower", "Spiral", "SuperMegaCloud"],
"reach": ["Planned", "Unplanned"],
"grasp": ["Can"],
"random": ["Randomness"],
}
#-- 二维与三维任务的区分
DIMENSION = {
"BostonCA": 2, "BostonCU": 2, "HarvardCA": 2, "HarvardCU": 2,
"Circle": 2, "Ellipse": 2, "Triangle": 2, "Flower": 2,
"Spiral": 2, "SuperMegaCloud": 2, "Planned": 2, "Unplanned": 2,
"Can": 3, "Randomness": 3,
}
def group_of(task: str) -> str:
#-- 找不到词根时返回 unknown,避免静默归错组
for g, members in GROUPS.items():
if task in members:
return g
return "unknown"
这段映射表在实际分析里比看上去重要。做对照实验时,通常不能把十四类任务混在一起统计,因为书写与随机运动在速度量级上差得很远。先按角色分组,再在组内做比较,是这份数据最自然的用法。
附录 E:如果只记五件事
- 它是手部三维轨迹,不是肌电、脑电或影像,通道只有时间加 x、y、z 三列。
- 规模是十名健康成年人、十四类任务,小到只能做机制研究,不能做规模训练。
- 采集在波士顿 Spaulding 康复医院运动分析实验室,用 VICON 系统,2018 年 8 月上线。
- 语义全部挂在文件名上,数值本身不带任务信息,任何流程第一步都是文件名解析。
- 论文的方法段是数据包之外的必需品,采样率、滤波、试次规则都不在数据里。
编辑说明
本页依据 PhysioNet 公开项目页与配套论文的引用信息撰写,事实核实时间为 2026 年 10 月 28 日。凡官方页面未给出数值的项目,一律标注为"官方未公布",未做推断填充;凡需要下载全量数据才能得到的统计量,本页未给出,留待使用者自行计算。文中对设备特性的一般性说明来自光学动作捕捉的通行工程常识,已与官方声明区分标注。若后续官方页面更新或论文补充材料发布,以官方为准。
相关数据集导航
以下为站内 AI-Ready 数据集百科中与本词条共享多个主题标签的相关数据集,按相关度降序排列:
- ppg-dalia — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- nesfdb — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- multi-gait-posture — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- wearable-device-dataset — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- semg-gait-31subjects — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- pamap2 — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- mhealth — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- uci-har — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- wearable-exercise-frailty — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
- kinecal — 共享标签:生理信号 / 步态与运动 / 可穿戴传感
导航说明:本章节由全站统一标签体系自动计算生成(标签重合度算法),双向可达;点击链接可跳转至对应数据集词条。

