Pregunta

Uh, sí, realmente necesitaría una rápida aportación de alguien sin los ojos del creador.Algo anda mal aquí, según mi scalacheck pruebas...pero realmente no sé lo suficiente como para saber dónde está mal.

case class Matrix(_1: (Float, Float, Float, Float), _2: (Float, Float, Float, Float),
                  _3: (Float, Float, Float, Float), _4: (Float, Float, Float, Float)) extends Immutable {
  def invert = {
    val _11 = _2._2 * _3._3 * _4._4 - _2._2 * _3._4 * _4._3 - _3._2 * _2._3 * _4._4
      +_3._2 * _2._4 * _4._3 + _4._2 * _2._3 * _3._4 - _4._2 * _2._4 * _3._3
    val _21 = -_2._1 * _3._3 * _4._4 + _2._1 * _3._4 * _4._3 + _3._1 * _2._3 * _4._4
      -_3._1 * _2._4 * _4._3 - _4._1 * _2._3 * _3._4 + _4._1 * _2._4 * _3._3
    val _31 = _2._1 * _3._2 * _4._4 - _2._1 * _3._4 * _4._2 - _3._1 * _2._2 * _4._4
      +_3._1 * _2._4 * _4._2 + _4._1 * _2._2 * _3._4 - _4._1 * _2._4 * _3._2
    val _41 = -_2._1 * _3._2 * _4._3 + _2._1 * _3._3 * _4._2 + _3._1 * _2._2 * _4._3
      -_3._1 * _2._3 * _4._2 - _4._1 * _2._2 * _3._3 + _4._1 * _2._3 * _3._2
    val _12 = -_1._2 * _3._3 * _4._4 + _1._2 * _3._4 * _4._3 + _3._2 * _1._3 * _4._4
      -_3._2 * _1._4 * _4._3 - _4._2 * _1._3 * _3._4 + _4._2 * _1._4 * _3._3
    val _22 = _1._1 * _3._3 * _4._4 - _1._1 * _3._4 * _4._3 - _3._1 * _1._3 * _4._4
      +_3._1 * _1._4 * _4._3 + _4._1 * _1._3 * _3._4 - _4._1 * _1._4 * _3._3
    val _32 = -_1._1 * _3._2 * _4._4 + _1._1 * _3._4 * _4._2 + _3._1 * _1._2 * _4._4
      -_3._1 * _1._4 * _4._2 - _4._1 * _1._2 * _3._4 + _4._1 * _1._4 * _3._2
    val _42 = _1._1 * _3._2 * _4._3 - _1._1 * _3._3 * _4._2 - _3._1 * _1._2 * _4._3
      +_3._1 * _1._3 * _4._2 + _4._1 * _1._2 * _3._3 - _4._1 * _1._3 * _3._2
    val _13 = _1._2 * _2._3 * _4._4 - _1._2 * _2._4 * _4._3 - _2._2 * _1._3 * _4._4
      +_2._2 * _1._4 * _4._3 + _4._2 * _1._3 * _2._4 - _4._2 * _1._4 * _2._3
    val _23 = -_1._1 * _2._3 * _4._4 + _1._1 * _2._4 * _4._3 + _2._1 * _1._3 * _4._4
      -_2._1 * _1._4 * _4._3 - _4._1 * _1._3 * _2._4 + _4._1 * _1._4 * _2._3
    val _33 = _1._1 * _2._2 * _4._4 - _1._1 * _2._4 * _4._2 - _2._1 * _1._2 * _4._4
      +_2._1 * _1._4 * _4._2 + _4._1 * _1._2 * _2._4 - _4._1 * _1._4 * _2._2
    val _43 = -_1._1 * _2._2 * _4._3 + _1._1 * _2._3 * _4._2 + _2._1 * _1._2 * _4._3
      -_2._1 * _1._3 * _4._2 - _4._1 * _1._2 * _2._3 + _4._1 * _1._3 * _2._2
    val _14 = -_1._2 * _2._3 * _3._4 + _1._2 * _2._4 * _3._3 + _2._2 * _1._3 * _3._4
      -_2._2 * _1._4 * _3._3 - _3._2 * _1._3 * _2._4 + _3._2 * _1._4 * _2._3
    val _24 = _1._1 * _2._3 * _3._4 - _1._1 * _2._4 * _3._3 - _2._1 * _1._3 * _3._4
      +_2._1 * _1._4 * _3._3 + _3._1 * _1._3 * _2._4 - _3._1 * _1._4 * _2._3
    val _34 = -_1._1 * _2._2 * _3._4 + _1._1 * _2._4 * _3._2 + _2._1 * _1._2 * _3._4
      -_2._1 * _1._4 * _3._2 - _3._1 * _1._2 * _2._4 + _3._1 * _1._4 * _2._2
    val _44 = _1._1 * _2._2 * _3._3 - _1._1 * _2._3 * _3._2 - _2._1 * _1._2 * _3._3
      +_2._1 * _1._3 * _3._2 + _3._1 * _1._2 * _2._3 - _3._1 * _1._3 * _2._2

    val det = _1._1 * _11 + _1._2 * _21 + _1._3 * _31 + _1._4 * _41
    if (det == 0) this
    else Matrix(
      (_11, _12, _13, _14),
      (_21, _22, _23, _24),
      (_31, _32, _33, _34),
      (_41, _42, _43, _44)
    ) * (1 / det)
  }

  def *(f: Float) = Matrix(
    (_1._1 * f, _1._2 * f, _1._3 * f, _1._4 * f),
    (_2._1 * f, _2._2 * f, _2._3 * f, _2._4 * f),
    (_3._1 * f, _3._2 * f, _3._3 * f, _3._4 * f),
    (_4._1 * f, _4._2 * f, _4._3 * f, _4._4 * f)
  )
}

Además, ¿puedo cargar esta Matrix en OpenGL o tengo que transponerla primero?Realmente siempre me confundo con estas matemáticas.

¿Fue útil?

Solución

Mira a Matriz reversible:Solución analítica en Wikipedia.El conjunto completo de cálculos en la parte superior calcula el conjugar de la matriz, a partir de la cual se calcula el determinante, y luego se obtiene la inversa 1 / det veces la matriz adjunta.

enter image description here

Todo el cálculo está escrito explícitamente para una matriz de 4 x 4 en su código, por lo que si hay un error, será necesario un poco de esfuerzo para verificarlo todo.Los artículos de Wikipedia explican cómo se supone que funciona.

Otros consejos

Invertir una matriz suele ser una mala idea, porque los cálculos pueden estar mal condicionados.

Si desea resolver un sistema de ecuaciones, es una mejor idea hacerlo usando algo como la descomposición LU y la sustitución hacia adelante y hacia atrás, especialmente si puede reutilizar la descomposición para resolver varios vectores del lado derecho.

Este enlace muestra un ejemplo de Java para la eliminación gaussiana con pivote.

Aquí hay otro pensamiento:tal vez puedas usar bibliotecas Java como Apache Commons Matemáticas, el sucesor de JAMA, en su solicitud?

Si tiene un caso particular en mente, le recomiendo ingresarlo en Wolfram Alpha para que puedas ver cuál debería ser la respuesta antes de comenzar a codificar.

Estoy bastante seguro Simplex3D implementa este cálculo (y muy probablemente se hace correctamente allí).

Si quieres jugar con números, hazlo tú mismo, tienes algunas buenas sugerencias de Jesper y duffymo (la inversión de matrices no es útil en la práctica; analiza la descomposición LU).

Sin embargo, si solo quieres Hacer las cosasMT examinar escalala y Scalalab.

De cualquier manera necesitarás Fondo de álgebra lineal conocimiento, que es una matemática increíblemente útil para muchos campos.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top