zoukankan      html  css  js  c++  java
  • Matplotlib学习---用mplot3d画莫比乌斯环(Mobius strip)

    mplot3d是matplotlib里用于绘制3D图形的一个模块。关于mplot3d 绘图模块的介绍请见:https://blog.csdn.net/dahunihao/article/details/77833877

    莫比乌斯环(mobius strip)是一种只有一个曲面的拓扑结构。把一个纸条扭转180°后,两头再粘接起来,这样的纸带只有一个面(即单侧曲面),一只小虫可以爬遍整个曲面而不必跨过它的边缘。

    莫比乌斯环是一个二维的紧致流形 (即一个有边界的面),可以嵌入到三维或更高维的流形中 。那么如何在3D空间上画莫比乌斯环呢?可以利用现有的方程式,将莫比乌斯环的两个参数(角度,宽度)映射到三维空间中。以下摘自维基百科(https://en.wikipedia.org/wiki/M%C3%B6bius_strip):

    """

    One way to represent the Möbius strip as a subset of three-dimensional Euclidean space is using the parametrization:

    x(u,v)=left(1+{frac {v}{2}}cos {frac {u}{2}}
ight)cos u
    y(u,v)=left(1+{frac {v}{2}}cos {frac {u}{2}}
ight)sin u
    z(u,v)={frac {v}{2}}sin {frac {u}{2}}

    where 0 ≤ u < 2π and −1 ≤ v ≤ 1. This creates a Möbius strip of width 1 whose center circle has radius 1, lies in the xyplane and is centered at (0, 0, 0). The parameter u runs around the strip while v moves from one edge to the other.

    """

    大概的意思就是:这个方程组可以创造一个宽度为1,中心圆半径为1的莫比乌斯环,其所处位置为x-y平面,中心为(0,0,0)。参数u绕整个环转圈,参数v则从一个边缘移动到另一个边缘。

    下面让我们一步一步来画莫比乌斯环。首先导入numpy,matplotlib和其3D模块,创建一个图形和一个三维坐标轴:

    import numpy as np
    import matplotlib.pyplot as plt
    from mpl_toolkits.mplot3d import Axes3D
    fig = plt.figure()
    ax = plt.axes(projection='3d')

    其次,定义u,v参数(u为绕环一圈的角度,v为环的宽度):

    u = np.linspace(0, 2*np.pi, endpoint=True, num=50)
    v = np.linspace(-1, 1, endpoint=True, num=10)

    然后,按照方程式,将u,v参数映射到三维空间(x轴,y轴和z轴):

    u,v=np.meshgrid(u,v)
    u=u.flatten()
    v=v.flatten()
    x = (1 + 0.5 * v * np.cos(u / 2.0)) * np.cos(u)
    y = (1 + 0.5 * v * np.cos(u / 2.0)) * np.sin(u)
    z = 0.5 * v * np.sin(u / 2.0)

    最后,选一个好看的配色方案,画出图像:

    ax.plot_trisurf(x,y,z,cmap="cool")

    此时图像如下:

    可以看出图像已基本成型,但是部分地方还有缺角。这是因为三角剖分还不正确。可以使用matplotlib现成的方法定义三角剖分:

    import matplotlib.tri as mtri
    tri = mtri.Triangulation(u, v)

    最后的最后,把图像变大一点,把x轴,y轴和z轴的上下限修改一下,这样图像看起来更好一些。

    完整代码如下:

    import numpy as np
    import matplotlib.pyplot as plt
    from mpl_toolkits.mplot3d import Axes3D
    fig = plt.figure(figsize=(10,6))
    ax = plt.axes(projection='3d')
    
    # u, v are parameterisation variables
    u = np.linspace(0, 2*np.pi, endpoint=True, num=50)
    v = np.linspace(-1, 1, endpoint=True, num=10)
    
    # This is the Mobius mapping, taking a u, v pair and returning an x, y, z
    # triple
    u,v=np.meshgrid(u,v) #用meshgrid函数来产生三维绘图时的矩阵
    u=u.flatten() #把u展开,变成一维数组
    v=v.flatten() #把v展开,变成一维数组
    x = (1 + 0.5 * v * np.cos(u / 2.0)) * np.cos(u)
    y = (1 + 0.5 * v * np.cos(u / 2.0)) * np.sin(u)
    z = 0.5 * v * np.sin(u / 2.0)
    
    # Triangulate parameter space to determine the triangles
    import matplotlib.tri as mtri
    tri = mtri.Triangulation(u, v)
    
    # Plot the surface.  The triangles in parameter space determine which x, y, z
    # points are connected by an edge.
    ax.plot_trisurf(x,y,z,cmap="cool",triangles=tri.triangles)
    ax.set_xlim(-1.1, 1.1)
    ax.set_ylim(-1.1, 1.1)
    ax.set_zlim(-1, 1)
    
    plt.show()

    图像如下:

     

    参考:https://matplotlib.org/gallery/mplot3d/trisurf3d_2.html?highlight=mobius

  • 相关阅读:
    zoj 3599 Game 博弈论
    hdu 2486/2580 / poj 3922 A simple stone game 博弈论
    hdu 1517 A Multiplication Game 博弈论
    hdu 4407 Sum 容斥原理
    hdu 4686 Arc of Dream
    hdu 4588 Count The Carries
    hdu 4586 Play the Dice
    C#学习(5)
    C#学习(4)
    C#学习(3)
  • 原文地址:https://www.cnblogs.com/HuZihu/p/9441217.html
Copyright © 2011-2022 走看看