6

12 面体の頂点をアルゴリズムで生成するにはどうすればよいですか?

四面体の重心を にしたいと思い(0, 0, 0)ます。

4

4 に答える 4

10

ウィキペディアから:

次のデカルト座標は、原点を中心とし、適切にスケーリングおよび方向付けされた 12 面体の頂点を定義します。

(±1、±1、±1)

(0、±1/φ、±φ)

(±1/φ、±φ、0)

(±φ、0、±1/φ)

ここで、φ = (1 + √5) / 2 は黄金比 (τ とも表記) ≈ 1.618 です。辺の長さは 2/φ = √5 – 1 です。含まれる球の半径は √3 です。

この説明は、大きな C# コードよりもはるかに簡潔で有益であることがわかりました。(-:

于 2012-10-29T08:30:42.237 に答える
6

質問がGoogle検索の上位の結果になっているので(数学での重複は#2です)、コードを追加したほうがよいと思いました。

完全なコンソールプログラムは以下のとおりであり、コンパイルして実行する必要があり、一般的に自明です。

アルゴリズムはウィキペディアの記事に基づいていました(ありがとう、math.stackoverflow.comのmt_

このコードは、頂点の正しいリストを出力するはずです。あなたの懸念は主にメソッドにありますが、モックオブジェクトProgram.MakeDodecahedronの代わりに独自の頂点データ構造を使用するようにこれを変更する必要があるため、単にコピーして貼り付けるのではありません。XNAのVector3Vertexを簡単に使用できます。これには、私のとまったく同じ署名を持つコンストラクターがあります。また、私の方法はハッキーなので、このプログラムを使用すると、見苦しい出力テーブルが出力される可能性があることに注意してください。VertexVertex.ToStringVector3

また、これは(不完全な)デモンストレーションであることに注意してください。たとえば、多くの四面体を生成する場合、呼び出しごとに定数(黄金比など)を不必要に再計算することになります。

XNAを使用すると、特にを使用する場合はMicrosoft.Xna.Framework、十二面体を3Dで簡単にレンダリングすることもできます。この目的のために、このチュートリアルのコードを適合させることができます。

using System;
using System.Collections.Generic;

namespace DodecahedronVertices
{
    class Program
    {
        static void Main()
        {
            // Size parameter: This is distance of each vector from origin
            var r = Math.Sqrt(3);

            Console.WriteLine("Generating a dodecahedron with enclosing sphere radius: " + r);

            // Make the vertices
            var dodecahedron = MakeDodecahedron(r);

            // Print them out
            Console.WriteLine("       X        Y        Z");
            Console.WriteLine("   ==========================");
            for (var i = 0; i < dodecahedron.Count; i++)
            {
                var vertex = dodecahedron[i];
                Console.WriteLine("{0,2}:" + vertex, i + 1);
            }

            Console.WriteLine("\nDone!");
            Console.ReadLine();
        }

        /// <summary>
        /// Generates a list of vertices (in arbitrary order) for a tetrahedron centered on the origin.
        /// </summary>
        /// <param name="r">The distance of each vertex from origin.</param>
        /// <returns></returns>
        private static IList<Vertex> MakeDodecahedron(double r)
        {
            // Calculate constants that will be used to generate vertices
            var phi = (float)(Math.Sqrt(5) - 1) / 2; // The golden ratio

            var a = 1 / Math.Sqrt(3);
            var b = a / phi;
            var c = a * phi;

            // Generate each vertex
            var vertices = new List<Vertex>();
            foreach (var i in new[] { -1, 1 })
            {
                foreach (var j in new[] { -1, 1 })
                {
                    vertices.Add(new Vertex(
                                        0,
                                        i * c * r,
                                        j * b * r));
                    vertices.Add(new Vertex(
                                        i * c * r,
                                        j * b * r,
                                        0));
                    vertices.Add(new Vertex(
                                        i * b * r,
                                        0,
                                        j * c * r));

                    foreach (var k in new[] { -1, 1 })
                        vertices.Add(new Vertex(
                                            i * a * r,
                                            j * a * r,
                                            k * a * r));
                }
            }
            return vertices;
        }
    }

    /// <summary>
    /// A placeholder class to store data on a point in space. Don't actually use this, write a better class (or just use Vector3 from XNA).
    /// </summary>
    class Vertex
    {
        double x;
        double y;
        double z;

        public Vertex(double x, double y, double z)
        {
            this.x = x;
            this.y = y;
            this.z = z;
        }

        public override string ToString()
        {
            var s = String.Format("{0,8:F2},{1,8:F2},{2,8:F2}", x, y, z);

            return s;
        }
    }
}

私のコードはおそらく非常に冗長で広まっているので、forループやその他のコード構造のフォールディングをサポートするもので読むことをお勧めします。

于 2012-05-05T13:14:41.060 に答える
2

P(0, 0, 0) を中心とする 12 面体と、半径 r の球で囲まれた頂点のデカルト座標は、次の式で与えられます。

P(±r/√3、±r/√3、±r/√3)

P(0, ± r/(√3*φ), ± (r*φ)/√3)

P(± r/(√3*φ), ± (r*φ)/√3, 0)

P(± (r*φ)/√3, 0, ± r/(√3*φ))

ここで、φ = (1 + √5) / 2 は黄金比 (τ とも表記) ≈ 1.618 です。

于 2013-10-18T23:01:03.373 に答える
1

これは、0頂点を中心とするリーマン面立体投影です。(申し訳ありませんが、数学記号を投稿する方法が見つかりません)

Tが黄金比である場合、a = 1 / T ^ 2とし、複素共役ペアb+-icをb=sqrt(5)/4およびc= sqrt(3)/4で定義します。これらの3つのポイントを0、120、および240度回転して、すべてが単位円の内側にある9つのポイントを作成します。

マップz->-1/ zを使用して、すべての点を単位円の外側の画像にマップします。ゼロと無限大にポイントを追加すると、12面体のすべての頂点が作成されます。

球上に12面体が必要な場合は、通常のステレオグラフィックバックマップを実行して、単位円を赤道上に配置します。通常の刻印プロセスでは、これによって頂点中心の立方体または四面体も得られますが、それぞれ約37.76度または22.24度回転します。

于 2012-12-12T01:42:20.980 に答える