使用Linq从嵌套数组中获取列的C#代码

8

如何使用Linq从嵌套数组的一列中获取元素作为扁平数组?

public class Matrix<T>
{
    private readonly T[][] _matrix;

    public Matrix(int rows, int cols)
    {
        _matrix = new T[rows][];
        for (int r = 0; r < rows; r++)
        {
            _matrix[r] = new T[cols];
        }
    }

    public T this[int x, int y]
    {
        get { return _matrix[x][y]; }
        set { _matrix[x][y] = value; }
    }

    // Given a column number return the elements
    public IEnumerable<T> this[int x]
    {
        get
        {
        }
    }
}

Matrix<double> matrix = new Matrix<double>(6,2);
matrix[0, 0] = 0;
matrix[0, 1] = 0;
matrix[1, 0] = 16.0;
matrix[1, 1] = 4.0;
matrix[2, 0] = 1.0;
matrix[2, 1] = 6.0;
matrix[3, 0] = 5.0;
matrix[3, 1] = 7.0;
matrix[4, 0] = 1.3;
matrix[4, 1] = 1.0;
matrix[5, 0] = 1.5;
matrix[5, 1] = 4.5;

3
嗯...你能提供输入数据和期望输出的示例吗? - digEmAll
1
给出你想要展开的数组的声明。 - sll
抱歉,我可能忘记了... - nixgadget
3个回答

13

这只是:

public IEnumerable<T> this[int x]
{
    get
    {
       return _matrix.Select(row => row[x]);
    }
}

当然,在进行LINQ查询之前最好检查x是否超出范围。 无论如何,考虑到您正在处理矩阵,为了更清晰,您可以切换到二维数组而不是交错数组(因此对于2个维度的大小没有疑问)。 相反,如果性能确实非常重要,请继续使用交错数组,它们似乎比二维数组快一些(例如LINK1LINK2)。

在我看来,这样会更好:_matrix.Where(array => array.Length > index).Select(array => array[index]) - Yuriy Rozhovetskiy
@YuriyRozhovetskiy:事实上,这个控件可以在查询之前制作,因为这个锯齿形数组构造时始终具有相同的列数。 - digEmAll
@digEmAll 我明白你的意思。这是因为不规则数组可以具有混合大小吗? - nixgadget
@kuzyt:是的,但这只是语法/清晰度的问题。如果性能真的很重要,那么锯齿数组似乎比多维数组快一点(请查看我的编辑)。 - digEmAll

2
var source = new int[3][] {
    Enumerable.Range(1,3).ToArray(),
    Enumerable.Range(10,5).ToArray(),
    Enumerable.Range(100,10).ToArray()
};

int index = 0;

var result = (from array in source
                from item in array
                group item by Array.IndexOf(array, item) into g
                where g.Key == index
                select g.ToArray()).FirstOrDefault();

0
var q = from row in jagged 
    from value in row 
    where value == anyvalue 
    select value; 

不过,你为什么想要使用LINQ呢?使用经典的for循环可以提高性能并使调试更容易。


你的where子句是基于值工作的,但为了始终选择相同的列,我认为它应该基于索引工作... - digEmAll
一般情况下我会使用经典的 for 循环,它更快且更易于调试。你应该只在需要提高可读性时使用 LINQ 对象,因为一般情况下经典的 for 循环比较快。 - Massimiliano Peluso

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