首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >寻找三维曲面的开口

寻找三维曲面的开口
EN

Stack Overflow用户
提问于 2015-09-16 12:52:17
回答 2查看 231关注 0票数 2

我有一个包含笛卡尔坐标XYZ的数组sphere。每一行都是对象表面的一个点。我想找出那个表面的开口,旋转物体,使x轴指向开口。

我正在使用python和numpy,但是一般的方法和特定的实现一样好。

这是我目前的情况。X轴为红色,原点为绿色:

我想要的是:

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-09-16 14:17:30

通常,您希望对数据应用旋转矩阵。但是,您还需要找到旋转矩阵。

在这种情况下,更容易直接跳过协方差矩阵的特征向量。这基本上是一种主成分方法。如果我们确定数据的主成分并将物体旋转到那个坐标系中,我们就能有效地做你想做的事情。

首先,让我们生成一个类似于您的示例:

代码语言:javascript
复制
import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D

def main():
    x, y, z = generate_data()
    plot(x, y, z)
    plt.show()

def generate_data():
    lat, lon = np.radians(np.mgrid[-90:90:20j, 0:180:20j])
    lon -= np.radians(40)
    z = np.cos(lat) * np.cos(lon)
    x = np.cos(lat) * np.sin(lon)
    y = np.sin(lat)
    return x, y, z

def plot(x, y, z):
    fig, ax = plt.subplots(subplot_kw=dict(projection='3d'), facecolor='w')
    artist = ax.scatter(x, y, z, marker='o', color='y')
    ax.set(xlim=[-1.1, 1.1], ylim=[-1.1, 1.1], zlim=[-1.1, 1.1], aspect=1)
    ax.set(xlabel='X', ylabel='Y', zlabel='Z')
    return artist

main()

现在我们可以根据主坐标旋转物体:

代码语言:javascript
复制
def reorient(x, y, z):
    xyz = np.vstack([x.ravel(), y.ravel(), z.ravel()])
    cov = np.cov(xyz)

    # Find the eigenvectors of the covariance matrix
    vals, vecs = np.linalg.eigh(cov)
    idx = np.argsort(vals)
    # The eigenvalues vals are not needed below, but this puts them in
    # the same order as the eigenvectors, should they be needed in future
    # versions of this code:
    vals, vecs = vals[idx], vecs[:, idx]

    # In this case, we actually want the second eigenvector to be the x-axis
    vecs = vecs[:, [1, 0, 2]]

    # Now let's perform a change-of-basis into the new coordinate system
    return np.linalg.inv(vecs).dot(xyz)

并绘制结果:

代码语言:javascript
复制
def main():
    x, y, z = generate_data()
    plot(*reorient(x, y, z))
    plt.show()

注意:我已经隐式地假设您的数据已经集中在旋转发生的点上。如果不是这样的话,在计算协方差矩阵之前,您需要减去旋转点(例如平均值),然后在基值变化后再将它加回去。

票数 4
EN

Stack Overflow用户

发布于 2015-09-16 14:15:09

这里有一个想法。拿出你的观点的凸包。如果你的表面的“开口”是平面的,那么这个开口将在凸起的外壳中被几乎共面覆盖。然后,所有人脸的法线向量将有一个不同的模式,这可以帮助识别边界。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/32609158

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档