BasicAI 标注数据格式规范

AI 的两大基石是算法和数据,BasicAI 作为一个 AI 数据标注平台,存在许多复杂结构的数据,这些数据基本都是半结构化的 JSON。本文讲解了 BasicAI 核心的 Data、Dataset、Classification、Class、Object 等对象的数据结构,以便第三方系统对接 BasicAI 平台,或者业内同行参考。

BasicAI 标注数据格式规范

BasicAI 是全球首个开源多模态训练数据平台,通过提供 AI 赋能的软件工具、数万项目提炼的本体中心和丰富的数据治理特性,来加速多模态训练数据的处理效率,进而提高 AI 工程师的建模效率。

通用约定

  1. 时间使用 UTC 时区的 ISO 8601 格式,比如 2012-03-29T10:05:45Z
  2. 需要 UUID 的地方统一使用 V4 版本,比如 6ec0bd7f-11c0-43da-975e-2a8ad9ebae0b
  3. 所有类型常量使用大写+下划线方式,比如 3D_BOX

Classification(类别) 定义

Classification 只有一个属性(Attribute),但属性可以多层嵌套,也就是选项(Option)还可以带属性。

{
    "id": 1,
    "attribute": {
        // ID
        "id": "64a16626-153f-4136-b7b4-572c10db08c3",
        // 名称
        "name": "品牌",
        // 类型
        // RADIO,DROPDOWN,TEXT,MULTI_SELECTION
        "type": "RADIO",
        // 是否必需
        "isRequired": true,
        // 选项
        "options": [
            {
                "id": "92f6b36c-0589-4310-bdc9-5b6918a9a2be",
                "name": "奔驰",
                "attributes": [
                    {
                        "id": "0fcb5add-4d2a-4d15-85e7-a8db966e6178",
                        "name": "型号",
                        "type": "RADIO",
                        "isRequired": false,
                        "options": [
                            {
                                "id": "b21e87ad-e096-44ba-a8aa-5adf7e7f5e10",
                                "name": "C300",
                                "attributes": [
                                    {
                                        "id": "69607032-9b53-4c95-90a8-6e378c19aa08",
                                        "name": "颜色",
                                        "type": "RADIO",
                                        "isRequired": false,
                                        "options": [
                                            {
                                                "id": "beb371c0-5cda-4738-987c-9b9022a4b2d4",
                                                "name": "黑色"
                                            },
                                            {
                                                "id": "d819cf06-ef0c-4e01-b787-8c89cfbf8578",
                                                "name": "白色"
                                            }
                                        ]
                                    }
                                ]
                            },
                            {
                                "id": "6798d905-9532-4ba0-bc1f-81bdb849e165",
                                "name": "GLE450",
                                "attributes": [
                                    {
                                        "id": "37d18428-b2e7-4fa0-93ce-9033497df1ec",
                                        "name": "颜色",
                                        "type": "RADIO",
                                        "isRequired": false,
                                        "options": [
                                            {
                                                "id": "6d007c39-d7cd-461a-9a07-1253718ae9cc",
                                                "name": "黑色"
                                            },
                                            {
                                                "id": "6e6533bf-e194-4294-be0e-941f09a00f9a",
                                                "name": "红色"
                                            }
                                        ]
                                    }
                                ]
                            }
                        ]
                    },
                    {
                        "id": "24ce829b-9b60-4b88-99f7-379b144a3cb3",
                        "name": "级别",
                        "type": "RADIO",
                        "isRequired": false,
                        "options": [
                            {
                                "id": "9dbdbe60-9a95-4f6f-9a4e-6bf84efb8382",
                                "name": "轿车"
                            },
                            {
                                "id": "e4497a0f-5c66-40a3-bce7-d9abc59ebbb3",
                                "name": "SUV"
                            }
                        ]
                    },
                    {
                        "id": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
                        "name": "动力",
                        "type": "MULTI_SELECTION",
                        "isRequired": false,
                        "options": [
                            {
                                "id": "14c9b60d-b4cb-475d-9cad-6dc8be58d67b",
                                "name": "汽油",
                                "attributes": [
                                    {
                                        "id": "9c0d296f-7141-4fd9-9cbe-c3d96a93d411",
                                        "name": "排量",
                                        "type": "RADIO",
                                        "isRequired": false,
                                        "options": [
                                            {
                                                "id": "bd290f13-5c04-4828-bf2c-2ccfbca31ef3",
                                                "name": "1.0L"
                                            },
                                            {
                                                "id": "4858b7e1-c86c-40a9-96cf-7d1c2aa6ec77",
                                                "name": "1.5L"
                                            },
                                            {
                                                "id": "973100cc-ae0a-4379-995f-a98fcf0c4944",
                                                "name": "2.0L"
                                            }
                                        ]
                                    }
                                ]
                            },
                            {
                                "id": "65f62053-e37a-42cf-98a4-b6e87e8b27a5",
                                "name": "柴油"
                            },
                            {
                                "id": "98b033e7-6c1c-4ade-95d5-684a5e6a26e0",
                                "name": "电池",
                                "attributes": [
                                    {
                                        "id": "8e790d10-9931-43f6-82bb-60619f1a25ea",
                                        "name": "容量",
                                        "type": "RADIO",
                                        "isRequired": false,
                                        "options": [
                                            {
                                                "id": "ea9080e5-ce3b-4df8-a55e-b4f53a1f1213",
                                                "name": "<20kWh"
                                            },
                                            {
                                                "id": "fec71b3d-a7db-4d6c-a68a-d9c66ec49c6e",
                                                "name": "20~50kWh"
                                            },
                                            {
                                                "id": "d995f663-766b-403c-bfef-ee6aa1ae0379",
                                                "name": "50~100kWh"
                                            },
                                            {
                                                "id": "7f90dbcd-f81e-4638-b342-4dad454bf728",
                                                "name": ">=100kWh"
                                            }
                                        ]
                                    }
                                ]
                            }
                        ]
                    }
                ]
            },
            {
                "id": "f7192a9a-ecee-4eb3-825c-5007c47c1c86",
                "name": "宝马"
            }
        ]
    }
}

Class(分类) 定义

Class 包含多个属性,暂不支持属性多层嵌套。

{
    // ID
    "id": 1,
    // Name
    "name": "Car",
    // 颜色
    "color": "#7dfaf2",
    // 工具类型
    // BOUNDING_BOX,CUBOID,POLYLINE
    "toolType": "CUBOID",
    // 工具选项
    "toolOptions": {},
    // 属性
    "attributes": [
        {
            "id": "bdc9acdf-4337-42de-8964-a1b5b6820287",
            "name": "品牌",
            "type": "RADIO",
            "isRequired": true,
            "options": [
                {
                    "id": "92f6b36c-0589-4310-bdc9-5b6918a9a2be",
                    "name": "奔驰"
                },
                {
                    "id": "f7192a9a-ecee-4eb3-825c-5007c47c1c86",
                    "name": "宝马"
                }
            ]
        },
        {
            "id": "0fcb5add-4d2a-4d15-85e7-a8db966e6178",
            "name": "型号",
            "type": "RADIO",
            "isRequired": true,
            "options": [
                {
                    "id": "b21e87ad-e096-44ba-a8aa-5adf7e7f5e10",
                    "name": "C300"
                },
                {
                    "id": "6798d905-9532-4ba0-bc1f-81bdb849e165",
                    "name": "GLE450"
                }
            ]
        },
        {
            "id": "24ce829b-9b60-4b88-99f7-379b144a3cb3",
            "name": "级别",
            "type": "RADIO",
            "isRequired": true,
            "options": [
                {
                    "id": "9dbdbe60-9a95-4f6f-9a4e-6bf84efb8382",
                    "name": "轿车"
                },
                {
                    "id": "e4497a0f-5c66-40a3-bce7-d9abc59ebbb3",
                    "name": "SUV"
                }
            ]
        },
        {
            "id": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
            "name": "动力",
            "type": "MULTI_SELECTION",
            "isRequired": true,
            "options": [
                {
                    "id": "14c9b60d-b4cb-475d-9cad-6dc8be58d67b",
                    "name": "汽油"
                },
                {
                    "id": "65f62053-e37a-42cf-98a4-b6e87e8b27a5",
                    "name": "柴油"
                },
                {
                    "id": "98b033e7-6c1c-4ade-95d5-684a5e6a26e0",
                    "name": "电池"
                }
            ]
        }
    ]
}

Data 信息格式

由于单个数据集下的数据量可能会非常大,所以无法直接导出数据文件,只能导出数据信息,里面包含数据的下载地址。

{
    // 格式版本
    "version": "1.0",
    // 数据 ID ,导入时无用
    "dataId": 1,
    // 类型
    // LIDAR_BASIC 纯点云数据,LIDAR_FUSION 点云融合数据,IMAGE 图片数据
    "type": "LIDAR_FUSION",
    // 名称
    "name": "08",
    
    // 以下为纯点云数据特有
    // 点云文件下载地址
    "pointCloudUrl": "https://basicai-prod-app-dataset.s3.us-west-2.amazonaws.com/1657877637263-90050/point_cloud/08.pcd"
    // 点云文件压缩包内路径,压缩包上传才有,导入时无用
    "pointCloudZipPath": "2022-11-11/point_cloud/08.pcd",
    
    // 以下为点云融合数据特有
    // 相机参数文件下载地址
    "cameraConfigUrl": "https://basicai-prod-app-dataset.s3.us-west-2.amazonaws.com/1657877637263-90050/camera_config/08.json",
    // 相机参数文件压缩包内路径,压缩包上传才有,导入时无用
    "cameraConfigZipPath": "2022-11-11/camera_config/08.json",
    // 相机图片信息,按相机编号排序
    "cameraImages": [
        {
            // 相机图片下载地址
            "url": "https://basicai-prod-app-dataset.s3.us-west-2.amazonaws.com/1657877637263-90050/image0/08.jpg",
            // 相机图片压缩包内路径,压缩包上传才有,导入时无用
            "zipPath": "2022-11-11/image0/08.jpg",
            "width": 1920,
            "height": 1080
        }
    ],
    // 点云文件下载地址
    "pointCloudUrl": "https://basicai-prod-app-dataset.s3.us-west-2.amazonaws.com/1657877637263-90050/point_cloud/08.pcd"
    // 点云文件压缩包内路径,压缩包上传才有,导入时无用
    "pointCloudZipPath": "2022-11-11/point_cloud/08.pcd",
    
    // 以下为图片数据特有    
    // 图片文件下载地址
    "imageUrl": "https://basicai-prod-app-dataset.s3.us-west-2.amazonaws.com/1657877637263-90050/point_cloud/08.pcd"
    // 图片文件压缩包内路径,压缩包上传才有,导入时无用
    "imageZipPath": "2022-11-11/point_cloud/08.pcd",
    "imageWidth": 1920,
    "imageHeight": 1080
}

Data 标注结果格式

由于标注结果以 Data 为粒度存储,因此 Data 标注结果格式需要同时支持内部存储和导入/导出两种场景。一个 Data 可能会通过多个来源标注,需要按来源区分标注结果。

  1. Object 表示框,每个框都归属到某个 Tracking Object,注意单帧里一个 Tracking Object 也可能包含多个框(比如点云 2/3D 融合标注),Object ID 为 UUID;
  2. 导入/导出基于内部存储格式,但去掉了仅内部使用的信息,比如 meta
  3. 有些信息在导入时无用,但内部存储又需要,会在导入时自动补上,比如 Object idversioncreatedBycreatedAt 等,反之,有些冗余信息内部存储里没有,但导出时需要加上;
  4. 点云分割需要将其中的点信息存放到单独的文件中,并在 JSON 里记录文件 URL,以避免 JSON 过大,导入/导出时如果是按 Data 划分文件可以直接将点信息放在文件中;
{
    // 格式版本
    "version": "1.0",
    // 数据 ID ,导入时无用
    "dataId": 1,
    // 结果来源 ID,导入时无用
    "sourceId": 1,
    // 结果来源类型,导入时只能为 EXTERNAL 相关类型
    // DATA_FLOW 数据流,TASK 工作流,MODEL 模型识别,EXTERNAL_GROUND_TRUTH 外部人工,EXTERNAL_MODEL 外部模型识别
    "sourceType": "TASK",
    // 结果来源名称
    "sourceName": "20221009000000",
   
    // 有效性,暂不支持导入
    "validity": "VALID",
    
    // 类别属性值,导入时如果提供,需同时在外层提供相关类别信息来新建,暂不支持导入
    "classificationValues": [
        {
            // 类别 ID
            "id": 1,
            // 类别取值,每层属性及其取值形成一个节点,节点之间通过 pid(属性 ID) 和 pvalue(属性值) 建立父子关系
            "values": [
                {
                    // 属性 ID
                    "id": "64a16626-153f-4136-b7b4-572c10db08c3",
                    // 父属性 ID,为 null 的是根节点
                    "pid": null,
                    // 仅用于父属性值为多选时,用来表示关联到哪个值
                    "pvalue": null,
                    "name": "品牌",
                    "type": "RADIO",
                    "value": "奔驰",
                    "alias": "牌子",
                    // 是否为叶子节点,注意定义里有可能为非叶子节点
                    "isLeaf": false
                },
                {
                    "id": "0fcb5add-4d2a-4d15-85e7-a8db966e6178",
                    "pid": "64a16626-153f-4136-b7b4-572c10db08c3",
                    "pvalue": null,
                    "name": "型号",
                    "type": "RADIO",
                    "value": "GLE450",
                    "alias": null,
                    "isLeaf": false
                },
                {
                    "id": "69607032-9b53-4c95-90a8-6e378c19aa08",
                    "pid": "0fcb5add-4d2a-4d15-85e7-a8db966e6178",
                    "pvalue": null,
                    "name": "颜色",
                    "type": "RADIO",
                    "value": "黑色",
                    "alias": null,
                    "isLeaf": true
                },
                {
                    "id": "24ce829b-9b60-4b88-99f7-379b144a3cb3",
                    "pid": "64a16626-153f-4136-b7b4-572c10db08c3",
                    "pvalue": null,
                    "name": "级别",
                    "type": "RADIO",
                    "value": "轿车",
                    "alias": null,
                    "isLeaf": true
                },
                {
                    "id": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
                    "pid": "64a16626-153f-4136-b7b4-572c10db08c3",
                    "pvalue": null,
                    "name": "动力",
                    "type": "MULTI_SELECTION",
                    "value": ["汽油", "电池"],
                    "alias": null,
                    "isLeaf": false
                },
                {
                    "id": "9c0d296f-7141-4fd9-9cbe-c3d96a93d411",
                    "pid": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
                    "pvalue": "汽油",
                    "name": "排量",
                    "type": "RADIO",
                    "value": "2.0L",
                    "alias": null,
                    "isLeaf": true
                },
                {
                    "id": "8e790d10-9931-43f6-82bb-60619f1a25ea",
                    "pid": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
                    "pvalue": "电池",
                    "name": "容量",
                    "type": "RADIO",
                    "value": "20~50kWh",
                    "alias": null,
                    "isLeaf": true
                }
            ]
        }
    ],
    
    // 对象(框)列表
    "objects": [
        // 3D 框
        {
            // ID,导入时无用,会自动补上
            "id": "6ec0bd7f-11c0-43da-975e-2a8ad9ebae0b",
            // 类型
            // 3D_BOX 3D 框,2D_RECT 2D 框,3D_SEGMENT_POINTS 3D 分割点云
            "type": "3D_BOX",
            // 更新版本,初始为 0,每改一次 +1,导入时无用,会自动补上
            "version": 1,
            // 创建者,导入时无用,会自动补上
            "createdBy": 1,
            // 创建时间,导入时无用,会自动补上
            "createdAt": "2012-03-29T10:05:45Z",
            
            // 追踪对象 ID
            "trackId": "J0lkBP7r",
            // 追踪对象名称
            "trackName": "Car 1",

            // 分类 ID,导入时如果提供,需同时在外层提供相关分类信息来新建
            "classId": 1,
            // 分类名称,存储和导入时无用,导出时自动补上
            "className": "Car",
            // 分类属性值,类似于 Classification,暂不支持多层嵌套
            "classValues": [
                {
                    "id": "bdc9acdf-4337-42de-8964-a1b5b6820287",
                    "pid": null,
                    "pvalue": null,
                    "name": "品牌",
                    "type": "RADIO",
                    "value": "奔驰",
                    "alias": "牌子",
                    "isLeaf": true
                },
                {
                    "id": "0fcb5add-4d2a-4d15-85e7-a8db966e6178",
                    "pid": null,
                    "pvalue": null,
                    "name": "型号",
                    "type": "RADIO",
                    "value": "GLE450",
                    "alias": null,
                    "isLeaf": true
                },
                {
                    "id": "24ce829b-9b60-4b88-99f7-379b144a3cb3",
                    "pid": null,
                    "pvalue": null,
                    "name": "级别",
                    "type": "RADIO",
                    "value": "轿车",
                    "alias": null,
                    "isLeaf": true
                },
                {
                    "id": "0669d8b1-f175-4f46-a8d2-cea7bf9dc1e2",
                    "pid": null,
                    "pvalue": null,
                    "name": "动力",
                    "type": "MULTI_SELECTION",
                    "value": ["汽油", "电池"],
                    "alias": null,
                    "isLeaf": true
                }
            ],
            
            // 模型识别置信度,只有模型识别时才有
            "modelConfidence": 0.83232,
            // 模型识别出来的分类,只有模型识别时才有
            "modelClass": "Person",
            
            // 轮廓信息,依具体框类型而不同
            "contour": {
                "points": [],
                "pointN": 3057,
                "size3D": { "x": 2.2125, "y": 4.993, "z": 1.38 },
                "center3D": { "x": 3.9220652257399284, "y": -6.013346632547687, "z": 0.39 },
                "rotation3D": { "x": 0, "y": 0, "z": -1.6622375116055483 }
            },
                        
            // 元信息,仅用于内部存储,导入/导出时无用
            "meta": {
                // 标注类型
                // 3D_LABEL 3D 标注,2D_LABEL 2D 标注,3D_SEGMENT 3D 分割,2D_SEGMENT 2D 分割
                "annotateType": "3D_LABEL",
                "classType":"",
                // "valid": true,
                // "checked": false,
                // "isProjection": false,
                // "invisibleFlag": false,
                // "resultType": "Dynamic",
                // "attrs": { "color": "#123" },
                // "resultStatus": "True_value",
                // "isStandard": false,
            }
        },
        
        // 2D 框
        {
            "id": "62383691-8077-44c2-ad8a-a6a7f54390c5",
            "type": "2D_BOX",
            "annotateType": "2D_LABEL",
            "version": "1",
            "createdBy": 1,
            "createdAt": "2012-03-29T10:05:45Z",
            
            "trackId": "c0627d18-1aa1-4788-ac88-09e8772ed9bb",
            "trackName": "Car 1",

            "classId": 1,
            "className": "",
            "classValues": {},

            "contour": {
                "points": [
                    { "x": 976.6271156786534, "y": 509.30442784738 },
                    { "x": 976.9704479066531, "y": 518.6737077997769 }
                ],
                "viewIndex": 3
            },
            
            "meta": {}
        },
        
        // 3D 点云分割
        {
            "id": "0d2c92c4-e96d-4672-abc7-a3480f412753",
            "type": "3D_SEGMENT_POINTS",
            "annotateType": "3D_SEGMENT",
            "version": "1",
            "createdBy": 1,
            "createdAt": "2012-03-29T10:05:45Z",
            
            "trackId": "c0627d18-1aa1-4788-ac88-09e8772ed9bb",
            "trackName": "Car 1",

            "classId": 1,
            "className": "",
            "classValues": {},

            "contour": {
                // 点云分割数据量较大,存放到文件中,仅用于内部存储
                "url": "https://basicai-prod-app-annotation.s3.us-west-2.amazonaws.com/tenant-1/dataset-1/data-flow/data-2/segment-points-0d2c92c4-e96d-4672-abc7-a3480f412753.json"
                // 用于导入/导出,由于点信息数据量较大,导出数据集标注结果时建议按 Data 划分 JSON 文件
                "points": []
            },
            
            "meta": {}
        }
    ]
}

Dataset 标注结果格式

Dataset 标注结果通过合并其下所有 Data 的标注结果来得到,不需要单独存储,因此只需支持导入/导出场景。

单个 JSON 文件

所有 Data 的标注结果合并到一个大的 JSON 文件中,适合数据量比较少的场景,比如 Data 数量不超过 1000 个。

  1. 将不同类型的信息独立开,避免互相干扰,降低理解成本,比如分离结果和数据信息使得结果信息可以采用简单的扁平结构,而数据信息可以采用多层结构(连续帧);
  2. JSON 里包含的 Data ID、Class ID 等均为外部 ID,即便是内部 ID,一旦导出就变成了外部 ID,再导入时会生成新的内部 ID,不能覆盖原有的记录。各类对象之间通过外部 ID 进行关联,比如 Object 所属的 Class;
{
    // 格式版本
    "version": "1.0",
    // 数据集 ID,导入时无用
    "datasetId": 1,
    // 数据集名字,导入时无用
    "datasetName": "LiDAR Fusion Trial",
    // 导出时间,导入时无用
    "exportTime": "2022-11-22T06:12:13.447Z",
    
    // 类别信息,具体结构参考 Classification 定义
    "classifications": [],
    
    // 分类信息,具体结构参考 Class 定义
    "classes": [],
    
    // 数据信息,具体结构参考 Data 信息格式
    "data": [],
    
    // 结果信息,具体结构参考 Data 标注结果格式
    "results": []
}

多个 JSON 文件

对于数据量很大的 Dataset,如果采用单个 JSON 文件,文件会非常大,打开时的资源消耗很大,甚至无法打开,特别是点云分割场景数据量就更大了,因此建议按 Data 划分 JSON 文件,然后打包成一个压缩包。

  1. 导入结果时需要同时导入数据,不支持将结果关联到已有数据;
  2. 对于大数据集,只导出数据信息,不导出数据文件,否则压缩包会非常大,需要的话可以依据数据信息里的地址去下载;
  3. 导出时不保留连续帧结构,因为连续帧只在标注时才有用,使用结果时不关心;
  4. 不支持基于数据信息的导入,因为要从网络下载大量文件,耗时很长且容易出错;
  5. 考虑到数据名称可能重复,因此导出时采用名称 + ID 的方式来作为单个 Data 导出文件的名称,导入时可以不管 ID,只要保证本次导入中文件名没有重复即可;

基于数据文件

点云数据集

.
├── camera_config // 相机参数
│   ├── 00-1.json
│   └── 01-2.json
├── image0 // 相机0图片
│   ├── 00-1.jpg
│   └── 01-2.jpg
├── image1 // 相机1图片
│   ├── 00-1.jpg
│   └── 01-2.jpg
├── image2 // 相机2图片
│   ├── 00-1.jpg
│   └── 01-2.jpg
├── point_cloud // 点云
│   ├── 00-1.pcd
│   └── 01-2.pcd
├── scene1 // 连续帧,其下结构参考根目录
├── result // 标注结果,具体结构参考 Data 标注结果格式
     ├── 00-1.json
     └── 01-2.json

图片数据集

.
├── image // 图片
│   ├── 00-1.jpg
│   └── 01-2.jpg
├── scene1 // 连续帧,其下结构参考根目录
└── result // 标注结果,具体结构参考 Data 标注结果格式
     ├── 00-1.json
     └── 01-2.json

基于数据信息

.
├── data // 数据信息,具体结构参考 Data 信息格式
│   ├── 00-1.json
│   └── 01-2.json
└── result // 标注结果,具体结构参考 Data 标注结果格式
     ├── 00-1.json
     └── 01-1.json