dkoontz
dkoontz

Reputation: 63

Can you access a C# multidimensional array indexer using an array?

I am trying to figure out if it's possible to pass an object as the index value for a multidimensional array.

var nums = new int[3,3];
// of course you can index by literal integers
nums[0, 2] = 99;
// but can you index by an array?  This does not work
var index = new [] {0, 2};
nums[index] = 100;

// I can use GetValue with the int array, but this returns an object not an int
nums.GetValue(new [] {0, 2});

So does anyone know what type I should be passing to the multidimensional array indexer to satisfy the compiler?

Upvotes: 3

Views: 1867

Answers (4)

Erik
Erik

Reputation: 12868

The short answer is no, you cannot do this natively.

The slightly longer answer is yes, you can implement such behavior using extension methods. You can add an extension method that would apply to all arrays like so:

public static class ArrayExtender
{
    public static T GetValue<T>(this T[,] array, params int[] indices)
    {
        return (T)array.GetValue(indices);
    }

    public static void SetValue<T>(this T[,] array, T value, params int[] indices)
    {
        array.SetValue(value, indices);
    }

    public static T ExchangeValue<T>(this T[,] array, T value, params int[] indices)
    {
        var previousValue = GetValue(array, indices);
        array.SetValue(value, indices);

        return previousValue;
    }
}

With that you can use:

        var matrix = new int[3, 3];
        matrix[0, 2] = 99;

        var oldValue = matrix.GetValue(0, 2);
        matrix.SetValue(100, 0, 2);
        var newValue = matrix.GetValue(0, 2);

        Console.WriteLine("Old Value = {0}", oldValue);
        Console.WriteLine("New Value = {0}", newValue);

Output:

Old Value = 99
New Value = 100

In most cases there is an object-oriented answer to why you need this functionality and proper custom classes can be created to facilitate this. For example, I may have a chessboard that I create several classes with helper methods:

class GameBoard
{
  public GamePiece GetPieceAtLocation(Point location) { ... }
}

Upvotes: 3

user2711965
user2711965

Reputation: 1825

You can not do that directly, instead you can write a generic method which would use GetValue Like:

class MyGenericClass<T>
{
    public static T GetValue(T[,] array, params int[] indices) 
    {
        return (T)array.GetValue(indices);
    }
}

and later you can do:

int val = MyGenericClass<int>.GetValue(nums, new[] { 0, 2 });

Upvotes: 1

Aaron Palmer
Aaron Palmer

Reputation: 9012

No, c# arrays are only indexed by integer values. You will have to manually traverse your array with integers.

If you need to index by another type, consider using Dictionary<TKey, TValue>

Upvotes: 1

Kirk Woll
Kirk Woll

Reputation: 77606

No, you cannot do this. Array indexers are syntactical, they are not "virtual" arrays. That means it expects a series of expressions separated by a comma, not an expression that might represent an array.

Similarly, you can't pass a three element array to a method that expects three parameters (excepting params, of course).

Upvotes: 1

Related Questions