优化FPS与延迟
pipeline.setXLinkChunkSize(0))。示例代码请参见延迟测量。要启用10Gbps USB3模式(使用USB 3.2 Gen 2兼容线缆时),必须在Device构造函数中显式设置:
Python
1with dai.Device(maxUsbSpeed=dai.UsbSpeed.SUPER_PLUS) as device:| 项目 | 分辨率 | FPS | 设定FPS | 延迟 [ms] | 带宽 | 直方图 |
|---|---|---|---|---|---|---|
| Color (isp) | 1080P | 60 | 60 | 33 | 1.5 Gbps | 链接 |
| Color (isp) | 4K | 28.5 | 30 | 150 | 2.8 Gbps | 链接 |
| Color (isp) | 4K | 26 | 26 | 83(标准差:3.6) | 2.6 Gbps | / |
| Mono | 720P/800P | 120 | 120 | 24.5 | 442/482 Mbps | 链接 |
| Mono | 400P | 120 | 120 | 7.5 | 246 Mbps | 链接 |
- oak_bandwidth_test.py 结果:下行797 Mbps,上行264 Mbps。
- oak_latency_test.py 结果:平均5.2 ms,标准差6.2。
| 项目 | 分辨率 | FPS | 设定FPS | PoE延迟 [ms] | USB 延迟 [ms] | 带宽 |
|---|---|---|---|---|---|---|
| Color (isp) | 1080P | 25 | 25 | 51 | 33(标准差:0.8) | 622 Mbps |
| Color (isp) | 4K | 8 | 8 | 148 | 80(标准差:1.2) | 530 Mbps |
| Color (isp) | 4K | 8.5 | 10 | 530 | 80(标准差:1.3) | 663 Mbps |
| Mono | 400P | 90 | 90 | 12(标准差:5.0) | 8(标准差:0.47) | 184 Mbps |
| Mono | 400P | 110 | 110 | 16(标准差:9.4) | 8(标准差:0.45) | 225 Mbps |
- 延迟 测量的是帧时间戳(
imgFrame.getTimestamp())与主机收到帧时的时间戳(dai.Clock.now())之间的时间差。 - 直方图 显示了“帧到达主机时间”在各帧之间的变化。Y轴表示在该时间点出现的帧数量,X轴表示微秒。
- 带宽 是以指定分辨率和FPS传输帧所需的计算带宽。
编码帧
| 项目 | 分辨率 | FPS | 设定FPS | 主机接收时间 [ms] | 直方图 |
|---|---|---|---|---|---|
| Color视频 H.265 | 4K | 28.5 | 30 | 210 | 链接 |
| Color视频 MJPEG | 4K | 30 | 30 | 71 | 链接 |
| Color视频 H.265 | 1080P | 60 | 60 | 42 | 链接 |
| Color视频 MJPEG | 1080P | 60 | 60 | 31 | 链接 |
| Mono H.265 | 800P | 60 | 60 | 23.5 | 链接 |
| Mono MJPEG | 800P | 60 | 60 | 22.5 | 链接 |
| Mono H.265 | 400P | 120 | 120 | 7.5 | 链接 |
| Mono MJPEG | 400P | 120 | 120 | 7.5 | 链接 |
cv2.Mat的指针,而不是执行内存拷贝(当前的做法),因此性能提升取决于您使用的图像大小。 (注意:API有所不同,message_zero_copy分支上并非所有功能都可用。)PoE延迟
- 网络本身。例如,如果你在一个有很多节点的大型网络中,延迟将比直接连接更高。
- 带宽存在瓶颈:
- 计算机的网络接口卡设置,文档在此
- 100%的OAK Leon CSS(CPU)使用率。Leon CSS核心处理POE通信(参见文档),如果CPU使用率达到100%,它将无法以应有的速度处理通信。解决方法: 参见 CPU使用率 文档。
- 另一种可能的改进PoE延迟的方法是微调网络设置,例如MTU、TCP窗口大小等(详情见这里)
带宽
Command Line
14K NV12/YUV420 frames: 3840 * 2160 * 1.5 * 30fps * 8bits = 3 gbps
21080P NV12/YUV420 frames: 1920 * 1080 * 1.5 * 30fps * 8bits = 747 mbps
3720P NV12/YUV420 frames: 1280 * 720 * 1.5 * 30fps * 8bits = 331 mbps
4
51080P RGB frames: 1920 * 1080 * 3 * 30fps * 8bits = 1.5 gbps
6
7800P depth frames: 1280 * 800 * 2 * 30fps * 8bits = 492 mbps
8400P depth frames: 640 * 400 * 2 * 30fps * 8bits = 123 mbps
9
10800P mono frames: 1280 * 800 * 1 * 30fps * 8bits = 246 mbps
11400P mono frames: 640 * 400 * 1 * 30fps * 8bits = 62 mbps- 使用 VideoEncoder 在设备上对帧进行编码(H.264、H.265、MJPEG)
- 降低FPS/分辨率/流数量
测量操作时间
trace(参见 DepthAI调试级别),depthai将记录每个节点/进程的操作时间,如下所示。Command Line
1[SpatialDetectionNetwork(1)] [trace] SpatialDetectionNetwork syncing took '70.39142' ms.
2[StereoDepth(4)] [trace] Warp node took '2.2945' ms.
3[system] [trace] EV:0,S:0,IDS:27,IDD:10,TSS:2,TSN:601935518
4[system] [trace] EV:0,S:1,IDS:27,IDD:10,TSS:2,TSN:602001382
5[StereoDepth(4)] [trace] Stereo took '12.27392' ms.
6[StereoDepth(4)] [trace] 'Median+Disparity to depth' pipeline took '0.86295' ms.
7[StereoDepth(4)] [trace] Stereo post processing (total) took '0.931422' ms.
8[SpatialDetectionNetwork(1)] [trace] NeuralNetwork inference took '62.274784' ms.
9[StereoDepth(4)] [trace] Stereo rectification took '2.686294' ms.
10[MonoCamera(3)] [trace] Mono ISP took '1.726888' ms.
11[system] [trace] EV:0,S:0,IDS:20,IDD:25,TSS:2,TSN:616446812
12[system] [trace] EV:0,S:1,IDS:20,IDD:25,TSS:2,TSN:616489715
13[SpatialDetectionNetwork(1)] [trace] DetectionParser took '3.464118' ms.运行NN时减少延迟
增加NN资源
Python
1import depthai as dai
2
3pipeline = dai.Pipeline()
4# nn = pipeline.create(dai.node.NeuralNetwork)
5# nn = pipeline.create(dai.node.MobileNetDetectionNetwork)
6nn = pipeline.create(dai.node.YoloDetectionNetwork)
7nn.setNumInferenceThreads(1) # 默认使用2个线程
8nn.setNumNCEPerInferenceThread(2) # 默认每个线程使用1个NCEAVAILABLE_SHAVES / 2.Example of FPS & latency comparison for YoloV7-tiny:| NN resources | Camera FPS | Latency | NN FPS |
|---|---|---|---|
| 6 SHAVEs, 2x Threads (1NCE/Thread) | 15 | 155 ms | 15 |
| 6 SHAVEs, 2x Threads (1NCE/Thread) | 14 | 149 ms | 14 |
| 6 SHAVEs, 2x Threads (1NCE/Thread) | 13 | 146 ms | 13 |
| 6 SHAVEs, 2x Threads (1NCE/Thread) | 10 | 141 ms | 10 |
| 13 SHAVEs, 1x Thread (2NCE/Thread) | 30 | 145 ms | 11.6 |
| 13 SHAVEs, 1x Thread (2NCE/Thread) | 12 | 128 ms | 12 |
| 13 SHAVEs, 1x Thread (2NCE/Thread) | 10 | 118 ms | 10 |
降低相机 FPS 以匹配 NN FPS
- MIPI 读取
- ISP 处理
- 预览后处理
- NN 处理
- 传输到主机
- 最后,直到到达应用程序的额外延迟
NN 输入队列大小和阻塞行为
detNetwork.input.setBlocking(False),但队列大小不变,以下调整可能有助于改善延迟性能:添加 detNetwork.input.setQueueSize(1),同时将相机 FPS 调回 40,我们得到约 80..105ms 的延迟。 导致不确定性的原因之一是相机的产生速率(帧间隔 25ms)与 NN 完成并可以接受新帧处理的速率不匹配。