wpfwannabe
wpfwannabe

Reputation: 14877

Converting array/matrix initialization code from C++ to C#

I am in the middle of converting C++ code to C#. I am having trouble with some C++ array static initialization. Consider the following piece of C++:

int Values[][32] = {
   {}, {}, {1, 2, 3}, {1}
};

What this does is creates a matrix of 4x32 integers. I need to do same or similar in C# in as straightforward way as possible. I am looking to get either

static int[][] Values = {...};

...or

static int[,] Values = {...};

The thing is C# does not seem to allow array initialization with uneven sub-array sizes. Other than this, if one specifies new int[4,32] {...} then everything between curly braces must be of exactly 32 length. With C++ one can specify {1, 2, 3} and the compiler will fill in the rest of the missing array members with zeros.

[EDIT] I have tried using LINQ and got what I desire but it looks cumbersome.

Upvotes: 1

Views: 424

Answers (3)

dana
dana

Reputation: 18145

I deleted my previous answer and am adding another (less eloquent) one that should work.

// utility function you can put in a class
static int[] BuildArray32(params int[] values)
{
    int[] retVal = new int[32];
    Array.Copy(values, retVal, values.Length);
    return retVal;
}

// array initializer code
int[][] Values = {
    BuildArray32(),
    BuildArray32(),
    BuildArray32(1, 2, 3),
    BuildArray32(1),
};

EDIT Or you could make a builder class :)

class MatrixBuilder
{
    int width;
    List<int[]> rows;

    public MatrixBuilder(int width)
    {
        this.width = width;
        this.rows = new List<int[]>();
    }

    public MatrixBuilder Add(params int[] row)
    {
        int[] wideRow = new int[width];
        Array.Copy(row, wideRow, row.Length);
        rows.Add(wideRow);
        return this;
    }

    public int[][] ToMatrix()
    {
        return rows.ToArray();
    }
}

int[][] Values2 = new MatrixBuilder(32)
    .Add()
    .Add()
    .Add(1, 2, 3)
    .Add(1)
    .ToMatrix();

Upvotes: 1

dashton
dashton

Reputation: 2704

You can't do it in c#. you can either initialise the arrays all to zeros, then apply your known initial values afterwards:

        int[][] initAll = new []
                               {
                                   new int[32] ,
                                   new int[32] ,
                                   new int[32] ,
                                   new int[32] 
                               };

or initialize a jagged array:

int[][] initJagged = new[]
                               {
                                   new[] {1, 3, 5, 7, 9},
                                   new[] {1, 3, }, 
                                   new[] {1, 3,0,0,0,0,},
                                   new int[32] 
                               };

Upvotes: 0

Sergey Kalinichenko
Sergey Kalinichenko

Reputation: 726599

In C# the size of your array initializer must match the declared size of the array. You do not need to declare the size if you would like to avoid duplication.

If you need all entries to be of the same size, you can do it with a little helper function Expand, like this:

static int[] Expand(int[] src, int size) {
    var res = new int[size];
    Array.Copy(src, res, src.Length);
    return res;
}

static int[][] Values = new int[4][] {
    Expand(new[] {1}, 32) 
,   Expand(new[] {1,2,3}, 32) 
,   Expand(new[] {1,2,3}, 32) 
,   Expand(new[] {1,2,3, 4, 5}, 32) 
};

Upvotes: 2

Related Questions