¿Cómo usar 'ref' en tiempo de compilación?

struct Matrix(int row, int col){ /* ... */ }

// finds the inverse using Gauss–Jordan elimination
pure M inverse(M)(const ref M m){ /* ... */ }

La razón m es un ref is because of performance. Obviously, I don't want large matrices being copied around every time the inverse is needed, and this has worked fine so far.

But, it has become a problem in situations where the inverse is needed at compile time:

mixin template A(){

  alias Matrix!(3, 3) Matrix3x3;

  static Matrix3x3 computeSomeMatrix(){ }

  immutable Matrix3x3 _m = computeSomeMatrix();
  immutable Matrix3x3 _m_1 = inverse(computeSomeMatrix());  // error

To fix the error, I need to change m to a non-ref, but that means that matrices will be copied every time inverse() is called. What do I do?

preguntado el 31 de enero de 12 a las 16:01

Or just simply have both ref and non-ref inverse() variants? -

What is the exact error you're getting? ref should work at compile time, it's probably something else you're doing that's causing it. -

@Robert The error says that computeSomeMatrix() is not an lvalue. -

@CyberShadow hmm... inverse(M)(auto const ref M m){ } worked. Care to explain? -

@DejanLekic That's just code duplication. -

1 Respuestas

I see one of two options. One, create a version which takes an rvalue. It's frequently annoying when a function doesn't work with rvalues anyway. A simple wrapper is all you need:

pure M inverse(M)(const ref M m){ /* ... */ }
pure M inverse(M)(const M m){ inverse(m); }

Be careful that the const-ness of the parameters matches though, or you're going to get infinite recursion.

However, a better solution would be to use auto ref. This is what it was created for.

pure M inverse(M)(const auto ref M m){ /* ... */ }

The compiler will then use ref when appropriate and non-ref when appropriate without you having to worry about it.

Respondido 01 Feb 12, 07:02

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.