java - 使用谢尔宾斯基方法打印三角形时如何固定三角形位置

标签 java

我目前正在编写一个代码,使用递归打印出谢尔宾斯基三角形。我能够打印出基本情况的第一个中心三角形(n==1),以及基本情况周围的 3 个三角形(n==2),但在那之后(n==3,4 等)三角形的方向它们本身很奇怪,而且我似乎找不到代码中的错误在哪里导致三角形以这种方式定向。

我尝试过更改 Sierpinski() 函数的调用位置,并且尝试了几种不同的方法来表示 x 和 y 坐标(对应于三角形的底点)。 height 方法和filledTriangle 方法似乎工作正常,因为三角形是等边的并且它们被正确填充和打印。该错误似乎与谢尔宾斯基方法无关。基本情况 (n==1) 没问题,但问题肯定出在 sierpinski 方法的 else 分支中。

public class Sierpinski {
    // Height of an equilateral triangle whose sides are of the specified length. 
    public static double height(double length) 
    {
        double height = (Math.sqrt(3)/2) * length;

        return height;
    }

    // Draws a filled equilateral triangle whose bottom vertex is (x, y) 
    // of the specified side length. 
    public static void filledTriangle(double x, double y, double length) 
    {
        double[] xArray = {x - height(length)/Math.sqrt(3), x, x + height(length)/Math.sqrt(3)};
        double[] yArray = {y + height(length), y , y + height(length)};

        StdDraw.filledPolygon(xArray,yArray);
    }

    // Draws a Sierpinski triangle of order n, such that the largest filled 
    // triangle has bottom vertex (x, y) and sides of the specified length. 
    static void sierpinski(int n, double x, double y, double length) 
    {
        if (n == 1)
        {
            filledTriangle(x, y, length);
        }

        else
        {
            filledTriangle(x, y, length);

            //Triangle Up
            sierpinski(n - 1, x, y + height(length), length/2);

            //Triangle Left
            sierpinski(n - 1, x/2, y, length/2);

            //Triangle Right x/2 + .5
            sierpinski(n - 1, x/2 + .5, y, length/2);

        }
    }

    // Takes an integer command-line argument n; 
    // draws the outline of an equilateral triangle (pointed upwards) of length 1; 
    // whose bottom-left vertex is (0, 0) and bottom-right vertex is (1, 0); and 
    // draws a Sierpinski triangle of order n that fits snugly inside the outline. 
    public static void main(String[] args) 
    {
        int n = Integer.parseInt(args[0]);

        double[] originalX = {0, 0.5, 1};
        double[] originalY = {0, Math.sqrt(3)/2, 0};
        double x = 0.5;
        double y = 0;
        double length = 0.5;
        StdDraw.polygon(originalX, originalY);

        sierpinski(n, x, y, length);


    }
}

我得到了 n == 1 和 n == 2 所期望的结果,但之后我得到了意想不到的结果。

最佳答案

我不太确定您使用的是什么图形库,因此我转换为 Swing。但本质上,这是通过递归绘画来实现的,直到它低于一定的大小。每个三角形的位置都是用标准三角函数计算的。

public class Tri extends JPanel {
    public static void main(String[] args) {
        JFrame frame = new JFrame("Sierpinkski");
        frame.setLayout(new BorderLayout());
        frame.add(new Tri(), BorderLayout.CENTER);
        frame.pack();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setVisible(true);
    }

    public Tri() {
        setPreferredSize(new Dimension(1000, 1000));
    }

    @Override
    protected void paintComponent(Graphics g) {
        Graphics2D gr = (Graphics2D)g;
        super.paintComponent(g);
        paintTriangle(gr, 500, 500, 400);
    }

    private void paintTriangle(Graphics2D gr, float x, float y, float size) {
        if (size > .5) {
            float vert = (float) (size * Math.sin(Math.PI / 6));
            float horz = (float) (size * (float) Math.cos(Math.PI / 6));
            Path2D.Float path = new Path2D.Float();
            path.moveTo(x, y - size);
            path.lineTo(x + horz, y + vert);
            path.lineTo(x - horz, y + vert);
            path.closePath();
            gr.draw(path);
            paintTriangle(gr, x, y - size / 2, size / 2);
            paintTriangle(gr, x + horz / 2, y + vert / 2, size / 2);
            paintTriangle(gr, x - horz / 2, y + vert / 2, size / 2);
        }
    }
}

关于java - 使用谢尔宾斯基方法打印三角形时如何固定三角形位置,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58617316/

相关文章:

java - 从其他类调用 AsyncTack 并返回 null Android Studio

java - 使用ASM给外部类添加注解

java - Android Studio Mac Gradle 问题

java - JSF 与 EL 表达的困难

java - 使用 jsoup 删除外部标签和内部标签的最佳方法是什么

java - 带有图像的 GUI 窗口

java - 是否可以在 Vaadin 14 和 RouterLink 中添加 uri 的 #fragment 部分?

java - 如何解决用户在java中使用BufferedReader输入时出现的错误 "Incompatible types"?

Java 9 Zip End Header Not Found 异常

java - 使用 Maven Assembly Plugin 时,XFire NamespaceURI 不能为空