旋转二维数组45度

7

如何将行数为奇数的二维整数矩阵旋转45度?

例如:

int[] myArray = new int[,]   
{  
    {1, 0 ,1},  
    {0, 1 ,0},  
    {0, 0 ,0},  
} 

转换为

int[] rotatedArray = new int[,]   
{  
    {0, 1 ,0},  
    {0, 1 ,1},  
    {0, 0 ,0},  
}  

对于任何维度(3x3,5x5,7x7等),都适用以下的 IT 技术。 5x5
0 0 0 0 0  
2 0 0 0 0  
1 1 1 1 1  
0 0 0 0 0  
0 0 0 0 0 

转换成

1 2 0 0 0  
0 1 0 0 0  
0 0 1 0 0  
0 0 0 1 0  
0 0 0 0 1 

5x5

0 0 0 3 0  
0 0 0 3 0  
0 0 0 3 0  
0 0 0 3 0  
0 0 0 3 0 

转化为

0 0 0 0 0  
0 0 0 0 3  
0 0 0 3 0  
0 0 3 3 0  
0 3 0 0 0  
4个回答

2
这是我和一个朋友编写的代码,用于解决以下问题:
public static class ArrayExtensions
{
    public static Point RoundIndexToPoint(int index, int radius)
    {
        if (radius == 0)
            return new Point(0, 0);
        Point result = new Point(-radius, -radius);

        while (index < 0) index += radius * 8;
        index = index % (radius * 8);

        int edgeLen = radius * 2;

        if (index < edgeLen)
        {
            result.X += index;
        }
        else if ((index -= edgeLen) < edgeLen)
        {
            result.X = radius;
            result.Y += index;
        }
        else if ((index -= edgeLen) < edgeLen)
        {
            result.X = radius - index;
            result.Y = radius;
        }
        else if ((index -= edgeLen) < edgeLen)
        {
            result.Y = radius - index;
        }

        return result;
    }

    public static T[,] Rotate45<T>(this T[,] array)
    {
        int dim = Math.Max(array.GetLength(0), array.GetLength(0));

        T[,] result = new T[dim, dim];

        Point center = new Point((result.GetLength(0) - 1) / 2, (result.GetLength(1) - 1) / 2);
        Point center2 = new Point((array.GetLength(0) - 1) / 2, (array.GetLength(1) - 1) / 2);
        for (int r = 0; r <= (dim - 1) / 2; r++)
        {
            for (int i = 0; i <= r * 8; i++)
            {
                Point source = RoundIndexToPoint(i, r);
                Point target = RoundIndexToPoint(i + r, r);

                if (!(center2.X + source.X < 0 || center2.Y + source.Y < 0 || center2.X + source.X >= array.GetLength(0) || center2.Y + source.Y >= array.GetLength(1)))
                    result[center.X + target.X, center.Y + target.Y] = array[center2.X + source.X, center2.Y + source.Y];
            }
        }
        return result;
    }     
}

很好,我希望我能将它移植到JavaScript... :-# - Brian Patterson

0

这些矩阵只有4x4或3x3,我会尝试使用math.net,但我担心这个旋转太特殊了。 - Kikaimaru
4
这些是用于变换的旋转矩阵。完全不同的事情。 - Cloudanger

0

我认为我们有以下规则:

  1. 将矩阵想象成一组“没有中心的框架或盒子”,就像“俄罗斯套娃”一样。

  2. 位于边缘中心(顶部/左侧/右侧/底部)的元素向最近的角落顺时针移动。

  3. 角落向下一个中心顺时针移动。

  4. 既不是角落也不是中心的元素向下一个位置移动(顺时针),该位置与它们当前距离角落相同。

我已经开始编写一些代码,但我认为这并不简单,而且我还没有时间测试。


0

你可以在codesignal上看到我关于矩阵旋转的解决方案。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接