PnP(Perspective‑n‑Point)问题,就是在已知一组3D 世界坐标点和它们在同一张图像中的 2D 像素坐标对应关系下,求解相机的外参(旋转 RRR 和平移 ttt)。通俗地说,就是问:

“我知道这些现实世界里的点在哪里,也看到它们投影在图像上了,怎样算出相机当时的位置和朝向?”


1. 输入与输出

  • 输入

    1. nnn 个 3D 点在世界坐标系下的位置:{Xi=[Xi,Yi,Zi]⊤}\{\mathbf{X}_i = [X_i, Y_i, Z_i]^\top\}{Xi=[Xi,Yi,Zi]}
    2. 对应的 2D 像素点:{xi=[ui,vi]⊤}\{\mathbf{x}_i = [u_i, v_i]^\top\}{xi=[ui,vi]}
    3. 相机内参矩阵 KKK(焦距、主点等)
  • 输出

    • 相机相对于世界坐标系的旋转矩阵 R∈R3×3R\in\mathbb{R}^{3\times3}RR3×3
    • 相机光心到世界原点的平移向量 t∈R3t\in\mathbb{R}^{3}tR3

这样你就可以构造投影矩阵 P=K [R∣t]P = K\,[R\mid t]P=K[Rt],把任何世界点正确地映射到图像上。


2. 为什么需要 PnP?

  • 定位与导航:机器人或 AR/VR 设备,已知环境中若干特征点(如棋盘角点、标志物)后,利用 PnP 实时确定自身位置和朝向。
  • 增强现实:对准虚拟物体与真实场景,需精准知道相机姿态。
  • 三维重建/融合:在多帧中对齐不同视角,恢复完整三维模型。

3. 经典解法思路

  1. 最小解法(P3P)

    • 只用 3 对点,就能得到至多 4 个解。
    • 再结合第 4 对点/重投影误差最小,确定唯一解。
  2. 一般 PnP

    • 当点数 n>4n>4n>4 时,用最小二乘迭代优化(如 Levenberg–Marquardt)来最小化所有投影误差:

      min⁡R,t∑i=1n∥ xi−π(K [R∣t] Xi)∥2, \min_{R,t}\sum_{i=1}^n \bigl\|\,\mathbf{x}_i - \pi\bigl(K\,[R\mid t]\,\mathbf{X}_i\bigr)\bigr\|^2, R,tmini=1n xiπ(K[Rt]Xi) 2,

      其中 π(⋅)\pi(\cdot)π() 表示齐次坐标归一化。

  3. 高效算法

    • EPnP:基于控制点插值,复杂度线性于点数。
    • RPnPUPnP 等:改进数值稳定性和鲁棒性。
  4. RANSAC + PnP

    • 在有误匹配(outliers)时,先用 RANSAC 随机抽样去噪,再对内点运行 PnP,提升鲁棒性。

4. 在 OpenCV 中如何使用?

# world_points: Nx3 numpy array of 3D points
# img_points:   Nx2 numpy array of corresponding 2D points
# K:            3×3 camera intrinsic matrix

# 1. 调用 solvePnP
success, rvec, tvec = cv2.solvePnP(
    world_points, img_points, K, distCoeffs=None,
    flags=cv2.SOLVEPNP_EPNP  # 或 cv2.SOLVEPNP_ITERATIVE、cv2.SOLVEPNP_P3P 等
)

# 2. 将旋转向量 rvec 转为旋转矩阵
R, _ = cv2.Rodrigues(rvec)

# 3. 构造投影矩阵 P = K [R|t]
P = K @ np.hstack((R, tvec))

一句话总结

PnP 问题:已知 3D–2D 对应点,算出相机“在哪里、朝哪儿看”的经典几何问题,是视觉定位、AR、SLAM 等系统的基础。

Logo

中国智能体开发者社区,聚焦智能体与大模型开发,提供前沿资讯、实用工具链、开源项目及行业案例。通过技术沙龙、开发者大赛等活动,促进经验交流与协作,助力开发者快速构建创新智能应用。

更多推荐