点群データの平面推定_part2

やること

  • 平面の導出
  • RANSACの勉強

前回の記事

techsho.hatenablog.com

平面の推定(Open3d)

前回は、Point Cloudから最小二乗法を使って平面を推定した
今回は、Open3Dを使う

Point Cloudの処理は、Point Cloud Library(PCL)が有名ですが最近python利用者はOpen3Dを使う人が増えています
pipで簡単にインストールできますが、私の場合少しはまったのでその時の経験は過去の記事にあります。

techsho.hatenablog.com

では、Open3Dを使った平面推定を行います。

import numpy as np
import open3d as o3d
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import math
%matplotlib inline
# 係数 (ax + by + cz + d = 0)
A = 0; B = 0; C = -1; D = 1

points = []
for x in np.arange(0, 10, 0.5):
  for y in np.arange(0, 10, 0.5):
    for z in np.arange(0, 10, 0.5):
      if(abs(A*x + B*y + C*z + D) < 1e-8):
        points.append([x, y, z])
points = np.asarray(points).T

pcd = o3d.geometry.PointCloud()
pcd.points = o3d.utility.Vector3dVector(points.T)

plane_model, inliers = pcd.segment_plane(distance_threshold=0.01,
                                             ransac_n=3,
                                             num_iterations=250)
[a, b, c, d] = plane_model
print(f"Plane model: {a:.2f}x + {b:.2f}y + {c:.2f}z + {d:.2f} = 0")


fig = plt.figure()
ax = Axes3D(fig)
ax.set_xlabel("X")
ax.set_ylabel("Y")
ax.set_zlabel("Z")

ax.scatter3D(points[0],points[1],points[2])

plt.show()

出力結果 (Ax + By + z + C = 0)

Plane model: 0.00x + 0.00y + 1.00z + -1.00 = 0

ちなみにopen3Dのsegment_planeはRANSACの処理が入っているため、ノイズにも強い