views:

388

answers:

6

What's wrong with this C# code? I tried to overload the + operator to add two arrays, but got an error message as follows:

One of the parameters of a binary operator must be the containing type.

class Program
{
  public static void Main(string[] args)
  {
      const int n = 5;

      int[] a = new int[n] { 1, 2, 3, 4, 5 };
      int[] b = new int[n] { 5, 4, 3, 2, 1 };
      int[] c = new int[n];

      // c = Add(a, b);
      c = a + b;

      for (int i = 0; i < c.Length; i++)
      {
        Console.Write("{0} ", c[i]);
      }

      Console.WriteLine();
  }

  public static int[] operator+(int[] x, int[] y)
  // public static int[] Add(int[] x, int[] y)
  {
      int[] z = new int[x.Length];

      for (int i = 0; i < x.Length; i++)
      {
        z[i] = x[i] + y[i];
      }

      return (z);
  }
}
+1  A: 

When you want to overload le + operator between type AA and BB, you must do it in the class AA or BB and not in a class named Program (like you did).

Unfortunatly, you cannot write code in the Array class.

What you can do is to

  • create your own class that implements IList
  • and put the + operator on that class.

If you need more detailed implementation, just ask me.

Manitra Andriamitondra
+2  A: 

Its states that one of the parameters to the operator needs to be of the same type as the operator function is a member of. So if the operator function is a member of MyClass on of the parameters needs to be of type MyClass.

class MyClass
{
 ...

public static int[] operator+(MyClass x, int[] y)
  // public static int[] Add(int[] x, int[] y)
  {
      int[] z = new int[x.Length];

      for (int i = 0; i < x.Length; i++)
      {
        z[i] = x[i] + y[i];
      }

      return (z);
  }
}
Joakim Karlsson
+8  A: 

Operators must be declared inside a "related" class' body. For instance:

public class Foo
{
    int X;

    // Legal
    public static int operator+(int x, Foo y);

    // This is not
    public static int operator+(int x, int y);
}

Since you don't have access to the implementation of arrays, your best bet would be to either wrap your arrays in your own implementation so you can provide additional operations (and this is the only way to make the operator+ work.

On the other hand, you could define an extension method like:

public static class ArrayHelper
{
    public static int[] Add(this int[] x, int[] y) { ... }
}

The will still lead to natural calls (x.Add(y)) while avoiding to wrap arrays in your own class.

Bryan Menard
+1  A: 

You can only add operators to a type that you create yourself. A int[] is a built in type you can't add operators to it.

You could create your own class that encapsulates an array, and add the operator to it.

Guffa
A: 

You can use something like this:

class Program {
  static void Main(string[] args) {
    const int n = 5;

    var a = new int[n] { 1, 2, 3, 4, 5 }.WithOperators();
    var b = new int[n] { 5, 4, 3, 2, 1 };

    int[] c = a + b;

    for (int i = 0; i < c.Length; i++) {
      Console.Write("{0} ", c[i]);
    }

    Console.WriteLine();
  }
}

public static class Int32ArrayExtensions {
  public static Int32ArrayWithOperators WithOperators(this int[] self) {
    return self;
  }
}

public class Int32ArrayWithOperators {
  int[] _array;

  public Int32ArrayWithOperators(int[] array) {
    if (array == null) throw new ArgumentNullException("array");
    _array = array; 
  }

  public static implicit operator Int32ArrayWithOperators(int[] array) {
    return new Int32ArrayWithOperators(array); 
  }
  public static implicit operator int[](Int32ArrayWithOperators wrapper) {
    return wrapper._array;
  }

  public static Int32ArrayWithOperators operator +(Int32ArrayWithOperators left, Int32ArrayWithOperators right) {
    var x = left._array;
    var y = right._array;
    return x.Zip(y, (a, b) => a + b).ToArray();
  }
}

Based on a related post that I wrote.

Jordão