C# 实现返回转置项的IEnumerable交错数组

C# 实现返回转置项的IEnumerable交错数组,c#,linq,matrix,transpose,ienumerator,C#,Linq,Matrix,Transpose,Ienumerator,我自己也试过这么做,这让我头疼不已 我希望能够使用LINQ从T[key1][key2]中选择,在那里它实际上“看到”T[key2][key1](即,转置矩阵)。我想这样做的原因是,我不必手动转置数组项(这很慢),而是动态地为转置的数组项提供服务 不确定这是否可能 编辑:要添加此功能的示例,请执行以下操作: T[][或T[,]。选择(项=>item),其中项的类型为T[],作为第n个枚举器位置的集合 int[,] matrix = new int[2,2] {{1, 2}, {3, 4}}; ma

我自己也试过这么做,这让我头疼不已

我希望能够使用LINQ从
T[key1][key2]
中选择
,在那里它实际上“看到”
T[key2][key1]
(即,转置矩阵)。我想这样做的原因是,我不必手动转置数组项(这很慢),而是动态地为转置的数组项提供服务

不确定这是否可能

编辑:要添加此功能的示例,请执行以下操作:

T[][
T[,]
。选择(项=>item)
,其中
项的类型为
T[]
,作为第n个枚举器位置的集合

int[,] matrix = new int[2,2] {{1, 2}, {3, 4}};
matrix = matrix.Select(item => item); //Where .Select magically transposes
//Matrix is now {{1, 3}, {2, 4}}
这就是你的意思(它慢吗?)

var items=newint[,]{
{1,2,3,4,5,6},
{10,20,30,40,50,60},
{100,200,300,400,500,600},
};  
var transposed=newint[items.GetLength(1),items.GetLength(0)];
for(int row=0;row
要编写以转置顺序遍历数组的代码,只需编写正常遍历数组的代码即可;数组的
IEnumerable
实现使用了什么,但不是遍历外循环中的最低维度和内循环中的较高维度,而是将它们反向:

public static IEnumerable<T> TraverseTransposed<T>(this T[,] array)
{
    for (int j = 0; j < array.GetLength(1); j++)
        for (int i = 0; i < array.GetLength(0); i++)
            yield return array[i, j];
}
公共静态IEnumerable遍历转换(此T[,]数组)
{
对于(int j=0;j
你能举例说明你的意思吗?LINQ不是那样工作的。它不理解锯齿阵列的概念。我将使用一个
Transpose()
方法创建一个
Matrix
类型,该方法返回一个新的
Matrix
对象,该对象具有转置的值。还有,当你说“哪个慢”的时候,我不知道你的意思。你的意思是实现缓慢还是执行缓慢?所以,目前,我正在使用一些代码首先将整个数组转置到位,然后在此集合上使用LINQ。换位对我来说很有用,因为我想平均键2的值,而不是键1的值。我试图实现的是LINQ的枚举器,它枚举“交换”的键。不需要将整个数组复制到一个新数组中,只需以不同的顺序遍历它。这需要O(n)内存,而不是O(1)内存。嗨,不幸的是,我不太确定如何在我的情况下使用它。例如,我有
T[,]
我想
。选择(item=>item)
from,其中
item
类型为
T[]
作为第n个枚举数位置的集合。那么听起来你更喜欢锯齿状数组,而不是2d数组。是的,这在标题中,尽管
item
应该是
T[]
@Patrick您明确地将代码显示为2D数组,而不是锯齿数组。但无论如何,如果您想要返回整个数组,而不仅仅是序列,那么它就无法实现不只是转置整个内容的目的。拥有迭代器而不仅仅是预先转置整个内容的整个想法是为了避免复制所有数据都转移到另一个结构中,如果需要数组,而不是
IEnumerable
,则不能这样做。我很确定
t[][
是锯齿状的,
t[,]
dimensional…我想要一个迭代器而不是手动转置的原因是为了避免这一点-我可以通过使用
T[key2][key1]
轻松地用for循环“选择”,我想为LINQ提供迭代器来完成这一点。请参阅我在Q中编辑的示例。
public static IEnumerable<T> TraverseTransposed<T>(this T[,] array)
{
    for (int j = 0; j < array.GetLength(1); j++)
        for (int i = 0; i < array.GetLength(0); i++)
            yield return array[i, j];
}