Dada una matriz entera cuadrada como entrada, genera el determinante de la matriz.
Reglas
- Puede suponer que todos los elementos en la matriz, el determinante de la matriz y el número total de elementos en la matriz están dentro del rango representable de enteros para su idioma.
- Se permite emitir un valor decimal / flotante con una parte fraccional de 0 (por ejemplo, en
42.0
lugar de42
). - Las acumulaciones están permitidas, pero le recomendamos que incluya una solución que no las use.
Casos de prueba
[[42]] -> 42
[[2, 3], [1, 4]] -> 5
[[1, 2, 3], [4, 5, 6], [7, 8, 9]] -> 0
[[13, 17, 24], [19, 1, 3], [-5, 4, 0]] -> 1533
[[372, -152, 244], [-97, -191, 185], [-53, -397, -126]] -> 46548380
[[100, -200, 58, 4], [1, -90, -55, -165], [-67, -83, 239, 182], [238, -283, 384, 392]] -> 571026450
[[432, 45, 330, 284, 276], [-492, 497, 133, -289, -28], [-443, -400, 56, 150, -316], [-344, 316, 92, 205, 104], [277, 307, -464, 244, -422]] -> -51446016699154
[[416, 66, 340, 250, -436, -146], [-464, 68, 104, 471, -335, -442], [159, -407, 310, -489, -248, 370], [62, 277, 446, -325, 47, -193], [460, 460, -418, -28, 234, -374], [249, 375, 489, 172, -423, 125]] -> 39153009069988024
[[-246, -142, 378, -156, -373, 444], [186, 186, -23, 50, 349, -413], [216, 1, -418, 38, 47, -192], [109, 345, -356, -296, -47, -498], [-283, 91, 258, 66, -127, 79], [218, 465, -420, -326, -445, 19]] -> -925012040475554
[[-192, 141, -349, 447, -403, -21, 34], [260, -307, -333, -373, -324, 144, -190], [301, 277, 25, 8, -177, 180, 405], [-406, -9, -318, 337, -118, 44, -123], [-207, 33, -189, -229, -196, 58, -491], [-426, 48, -24, 72, -250, 160, 359], [-208, 120, -385, 251, 322, -349, -448]] -> -4248003140052269106
[[80, 159, 362, -30, -24, -493, 410, 249, -11, -109], [-110, -123, -461, -34, -266, 199, -437, 445, 498, 96], [175, -405, 432, -7, 157, 169, 336, -276, 337, -200], [-106, -379, -157, -199, 123, -172, 141, 329, 158, 309], [-316, -239, 327, -29, -482, 294, -86, -326, 490, -295], [64, -201, -155, 238, 131, 182, -487, -462, -312, 196], [-297, -75, -206, 471, -94, -46, -378, 334, 407, -97], [-140, -137, 297, -372, 228, 318, 251, -93, 117, 286], [-95, -300, -419, 41, -140, -205, 29, -481, -372, -49], [-140, -281, -88, -13, -128, -264, 165, 261, -469, -62]] -> 297434936630444226910432057
You may assume that all elements in the matrix, the determinant of the matrix, and the total number of elements in the matrix are within the representable range of integers for your language.
Respuestas:
Jalea , 15 bytes
Pruébalo en línea!
Cómo funciona
Por qué funciona - versión mathy
El operador det toma una matriz y devuelve un escalar. Una matriz n -by- n puede considerarse como una colección de n vectores de longitud n , por lo que det es realmente una función que toma n vectores de ℤ n y devuelve un escalar.
Por lo tanto, escribo det ( v 1 , v 2 , v 3 , ..., v n ) para det [ v 1 v 2 v 3 ... v n ].
Observe que det es lineal en cada argumento, es decir, det ( v 1 + λ w 1 , v 2 , v 3 , ..., v n ) = det ( v 1 , v 2 , v 3 , ..., v n ) + λ det ( w 1 , v 2 , v 3 , ..., v n ). Por lo tanto, es un mapa lineal de (ℤ n ) ⊗ n a ℤ.
Es suficiente determinar la imagen de la base bajo el mapa lineal. La base de (ℤ n ) ⊗ n consiste en productos tensor n- pliegues de los elementos básicos de ℤ n , es decir, ee 5 ⊗ e 3 ⊗ e 1 ⊗ e 5 ⊗ e 1 . Los productos tensores que incluyen tensores idénticos deben enviarse a cero, ya que el determinante de una matriz en la que dos columnas son idénticas es cero. Queda por comprobar a qué se envían los productos tensoriales de elementos básicos distintos. Los índices de los vectores en el producto tensor forman una biyección, es decir, una permutación, en la cual las permutaciones pares se envían a 1 y las permutaciones impares se envían a -1.
Por ejemplo, para encontrar el determinante de [[1, 2], [3, 4]]: tenga en cuenta que las columnas son [1, 3] y [2, 4]. Descomponemos [1, 3] para dar (1 e 1 + 3 e 2 ) y (2 e 1 + 4 e 2 ). El elemento correspondiente en el producto tensor es (1 e 1 ⊗ 2 e 1 + 1 e 1 ⊗ 4 e 2 + 3 e 2 ⊗ 2 e 1 + 3 e 2 ⊗ 4 e 2 ), que simplificamos a (2 e 1 ⊗ e 1 + 4 e 1 ⊗ e 2 + 6 e 2 ⊗ e 1 + 12 e 2 ⊗ e 2) Por lo tanto:
det [[1, 2], [3, 4]]
= det (1 e 1 + 3 e 2 , 2 e 1 + 4 e 2 )
= det (2 e 1 ⊗ e 1 + 4 e 1 ⊗ e 2 + 6 e 2 ⊗ e 1 + 12 e 2 ⊗ e 2 )
= det (2 e 1 ⊗ e 1 ) + det (4 e 1 ⊗ e 2 ) + det (6 e 2 ⊗ e 1 ) + det (12 e2 ⊗ e 2 )
= 2 det (e 1 ⊗ e 1 ) + 4 det (e 1 ⊗ e 2 ) + 6 det (e 2 ⊗ e 1 ) + 12 det (e 2 ⊗ e 2 )
= 2 (0) + 4 (1) + 6 (-1) + 12 (0)
= 4 - 6
= -2
Ahora queda por demostrar que la fórmula para encontrar la paridad de la permutación es válida. Lo que hace mi código es esencialmente encontrar el número de inversiones, es decir, los lugares donde un elemento a la izquierda es más grande que un elemento a la derecha (no necesariamente consecutivamente).
Por ejemplo, en la permutación 3614572, hay 9 inversiones (31, 32, 61, 64, 65, 62, 42, 52, 72), por lo que la permutación es impar.
La justificación es que cada transposición (intercambiando dos elementos) agrega una inversión o quita una inversión, intercambiando la paridad del número de inversiones, y la paridad de la permutación es la paridad del número de transposiciones necesarias para lograr la permutación.
Por lo tanto, en conclusión, nuestra fórmula viene dada por:
Por qué funciona - versión no matemática
donde σ es una permutación de 𝕊 n el grupo de todas las permutaciones de n cartas, y sgn es la señal de la permutación, AKA (-1) elevado a la paridad de la permutación, y un ij es el ( ij ) º entrada en la matriz ( i abajo, j a través).
fuente
R , 3 bytes
Solución trivial
Pruébalo en línea!
R ,
9492 bytessolución re-implementada
superado por Jarko Dubbeldam
Pruébalo en línea!
Utiliza de forma recursiva la expansión de menores en la primera columna de la matriz.
fuente
Jalea ,
16151210 bytesUtiliza la expansión de Laplace . ¡Gracias a @miles por jugar
35 bytes!Pruébalo en línea!
Cómo funciona
fuente
Wolfram Language (Mathematica) , entre 14 y 42 bytes
Hemos tenido una solución integrada de 3 bytes y una solución de 53 bytes que evita por completo las incorporaciones, por lo que aquí hay algunas soluciones más extrañas en algún punto intermedio.
Wolfram Language tiene muchas funciones muy intensas para descomponer matrices en productos de otras matrices con una estructura más simple. Uno de los más simples (lo que significa que he oído hablar de él antes) es la descomposición de Jordan. Cada matriz es similar a una matriz triangular superior (posiblemente de valor complejo) hecha de bloques diagonales con una estructura específica, llamada la descomposición de Jordan de esa matriz. La similitud preserva los determinantes, y el determinante de una matriz triangular es el producto de los elementos diagonales, por lo que podemos calcular el determinante con los siguientes 42 bytes :
El determinante también es igual al producto de los valores propios de una matriz, con multiplicidad. Afortunadamente, la función de valor propio de Wolfram realiza un seguimiento de la multiplicidad (incluso para matrices no diagonalizables), por lo que obtenemos la siguiente solución de 20 bytes :
La siguiente solución es hacer trampa y no estoy seguro de por qué funciona. El wronskiano de una lista de n funciones es el determinante de la matriz de las primeras n -1 derivadas de las funciones. Si le damos a la
Wronskian
función una matriz de enteros y decimos que la variable de diferenciación es 1, de alguna manera escupe el determinante de la matriz. Es raro, pero no involucra las letras "Det
" y solo tiene 14 bytes ...(El determinante Casoratian funciona tan bien, de 1 byte más:
#~Casoratian~1&
)En el ámbito de la álgebra del extracto, el determinante de un n x n de la matriz (idea de que el mapa k → k que es la multiplicación por el factor determinante) es la n ésima potencia exterior de la matriz (después de recoger un isomorfismo k → ⋀ n k n ) En el lenguaje Wolfram, podemos hacer esto con los siguientes 26 bytes :
Y aquí hay una solución que funciona solo para determinantes positivos. Si tomamos un hipercubo de unidad n- dimensional y le aplicamos una transformación lineal, el "volumen" n- dimensional de la región resultante es el valor absoluto del determinante de la transformación. Aplicar una transformación lineal a un cubo da un paralelepípedo, y podemos tomar su volumen con los siguientes 39 bytes de código:
fuente
Exp@*Tr@*MatrixLog
, pero desafortunadamente esto no funciona para matrices singulares.Check[E^Tr@MatrixLog@#,0]&
.Check
antes.Haskell , 71 bytes
-3 bytes gracias a Lynn. Otro bytes el polvo gracias a Craig Roy.
Pruébalo en línea! Se agregó una
-O
bandera para fines de optimización. No es necesario.Explicación (obsoleta)
f
implementa recursivamente la expansión del cofactor.Esta línea cubre el caso base de una matriz 1 × 1 , en cuyo caso el determinante es
mat[0, 0]
.Esto utiliza la coincidencia de patrones de Haskell para dividir la matriz en una cabeza (la primera fila) y una cola (el resto de la matriz).
Enumera la cabeza de la matriz (comprimiendo la lista infinita de números enteros y la cabeza) e itera sobre ella.
Niegue el resultado en función de si su índice es uniforme, ya que el cálculo del determinante implica sumas y restas alternadas.
Esto esencialmente elimina la i-ésima columna de la cola al tomar i elementos y concatenarla con la fila con los primeros (i + 1) th elementos eliminados para cada fila en la cola.
Calcule el determinante del resultado anterior y multiplíquelo con el resultado de
(-1)*i*v
.Suma el resultado de la lista anterior y devuélvelo.
fuente
sum[(-1)^i*...
confoldr(-)0[...
Protón , 99 bytes
Pruébalo en línea!
-3 bytes gracias al Sr. Xcoder
-3 bytes gracias a Erik the Outgolfer
Expansión sobre la primera fila
fuente
((~i%2)*2-1)
->((-i%2)|1)
j!=i
conj-i
oi-j
.Octava , 28 bytes
Pruébalo en línea!
Esto utiliza la descomposición QR de una matriz X en una matriz orthgonal Q y una matriz triangular superior R . El determinante de X es el producto de los de Q y R . Una matriz ortogonal tiene un determinante unitario, y para una matriz triangular, el determinante es el producto de sus entradas diagonales. De Octave
qr
función llamada con una sola salida da R .El resultado se redondea al entero más cercano. Para matrices de entrada grandes, las imprecisiones de coma flotante pueden producir un error superior
0.5
y, por lo tanto, producir un resultado incorrecto.fuente
det
edificio. ;)Haskell , 59 bytes
Pruébalo en línea!
fuente
C,
176125bytes¡Gracias a @ceilingcat por jugar 42 bytes y gracias a @Lynn y @Jonathan Frech por guardar un byte cada uno!
Calcula el determinante utilizando la expansión de Laplace a lo largo de la primera fila.
Pruébalo en línea!
Desenrollado:
fuente
(i%2*-2+1)
→(1-i%2*2)
guarda un byte más.n+1+c
puede sern-~c
.i=s
lugar dereturn s
Jalea , 43 bytes
¡Finalmente terminé de escribir mi solución no incorporada en un lenguaje de golf!
¡Gracias a HyperNeutrino por guardar un byte!
Pruébalo en línea! (código espaciado para mayor claridad)
La forma terriblemente larga de eliminar elementos n-ésimo de una lista, mejorará más tarde
Esta respuesta había sido superada por las respuestas de HyperNeutrino, Dennis y Leaky Nun. Jelly es muy popular como lenguaje de golf.
Explicación rápida:
fuente
Jalea , 24 bytes
Pruébalo en línea!
Explicación
-2 bytes gracias a la solución user202729
fuente
MATL , 3 bytes / 5 bytes
Con función incorporada
Pruébalo en línea!
Sin incorporado
Gracias a Misha Lavrov por señalar un error, ahora corregido
Pruébalo en línea!
Esto calcula el determinante como el producto de los valores propios, redondeado al entero más cercano para evitar imprecisiones de punto flotante.
fuente
R , 32 bytes
Utiliza el algoritmo de Not a Tree para tomar los valores propios de la matriz y tomar la parte real de su producto.
Pruébalo en línea!
fuente
Octava , 30 bytes
Pruébalo en línea!
o la solución aburrida de 4 bytes (ahorró 6 bytes gracias a Luis Mendo (olvidó las reglas que regulan las funciones integradas)):
Explicación:
¡Subiendo! :)
fuente
TI-Basic, 2 bytes
Ah bueno.
Por favor, no voten por respuestas triviales.
Como estudiante de secundaria (que se ve obligado a tener una de estas calculadoras), esta función es muy útil, así que ...
fuente
Haskell, 62 bytes
Pruébalo en línea! (Pie de página con casos de prueba tomados de la solución @ totallyhuman).
d
calcula el determinante usando una expansión de Laplace a lo largo de la primera columna. Necesita tres bytes más que el permanente .fuente
Python 2 , 95 bytes
-12 bytes gracias a Lynn.
Puerto de mi respuesta Haskell .
Pruébalo en línea!
fuente
[]
como caso base: ¡f=lambda m:sum((-1)**i*v*f([j[:i]+j[i+1:]for j in m[1:]])for i,v in enumerate(m[0]))if m else 1
para 95 bytes!m==[]or sum(...)
da 92 bytes.Wolfram Language (Mathematica) ,
5352 bytesPruébalo en línea!
Desafortunadamente, calcular el determinante de una matriz n por n de esta manera utiliza la memoria O ( n n ), lo que pone fuera del alcance los casos de prueba grandes.
Cómo funciona
La primera parte,
1##&@@@(t=Tuples)@#
calcula todos los productos posibles de un término de cada fila de la matriz dada.t[Range@Tr[1^#]&/@#]
da una lista de la misma longitud cuyos elementos son similares{3,2,1}
o{2,2,3}
dicen qué entrada de cada fila elegimos para el producto correspondiente.Aplicamos
Signature
a la segunda lista, que asigna permutaciones pares a1
, permutaciones impares a-1
, y no permutaciones a0
. Este es precisamente el coeficiente con el que el producto correspondiente aparece en el determinante.Finalmente, tomamos el producto escalar de las dos listas.
Si incluso
Signature
es demasiado incorporado, a 73 bytes podemos tomarreemplazándolo por
1##&@@Order@@@#~Subsets~{2}&
. Esto calculaSignature
una posible permutación tomando el producto deOrder
aplicado a todos los pares de elementos de la permutación.Order
dará1
si el par está en orden ascendente,-1
si está en orden descendente y0
si son iguales.-1 byte gracias a @ user202729
fuente
Python 3 ,
238 bytes,227 bytes,224 bytes, 216 bytesPruébalo en línea!
Mi solución utiliza la definición de un determinante para los cálculos. Desafortunadamente, la complejidad de este algoritmo es
n!
y no puedo mostrar el paso de la última prueba, pero en teoría esto es posible.fuente
CJam (
5045 bytes)Este es un bloque anónimo (función) que toma una matriz 2D en la pila y deja un número entero en la pila.
Conjunto de pruebas en línea
Disección
Esto implementa el algoritmo Faddeev-LeVerrier , y creo que es la primera respuesta para adoptar ese enfoque.
fuente
Wolfram Language (Mathematica) , 3 bytes
Pruébalo en línea!
Según el meta consenso , principalmente votan por soluciones no triviales que requieren esfuerzo para escribir.
fuente
Python 2 , 75 bytes
Pruébalo en línea!
fuente
SageMath , varios
Aquí hay un montón de métodos para calcular el determinante que encontré interesante, todos programados en SageMath. Todos pueden ser probados aquí .
Construido, 3 bytes
Este no es demasiado interesante. Sage proporciona alias de nivel global a muchas operaciones comunes que normalmente serían métodos de objeto, por lo que es más corto que
lambda m:m.det()
.Parte real del producto de valores propios, 36 bytes
Desafortunadamente,
eigenvalues
no es uno de esos alias a nivel global. Eso, combinado con el hecho de que Sage no tiene una forma ordenada de componer funciones, significa que estamos atrapados en un proceso costosolambda
. Los valores simbólicos de esta función se convierten automáticamente en valores numéricos cuando se imprimen, por lo que puede haber alguna inexactitud de coma flotante en algunas salidas.Producto de Diagonal en forma normal Jordan, 60 bytes
En la forma Jordan Normal, una matriz NxN se representa como una matriz de bloques, con N bloques en la diagonal. Cada bloque consta de un valor propio único o una matriz MxM con un valor propio repetido en la diagonal
1
ys en la super-diagonal (la diagonal arriba y a la derecha de la diagonal "principal"). Esto da como resultado una matriz con todos los valores propios (con multiplicidad) en la diagonal principal, y algunos1
s en la super-diagonal correspondiente a los valores propios repetidos. Esto devuelve el producto de la diagonal de la forma normal de Jordan, que es el producto de los valores propios (con multiplicidad), por lo que esta es una forma más indirecta de realizar el mismo cálculo que la solución anterior.Como Sage quiere que la forma normal de Jordan esté sobre el mismo anillo que la matriz original, esto solo funciona si todos los valores propios son racionales. Los valores propios complejos dan como resultado un error (a menos que la matriz original esté sobre el anillo
CDF
(flotadores dobles complejos) oSR
). Sin embargo, esto significa que tomar la parte real no es necesario, en comparación con la solución anterior.Producto de la Diagonal en la descomposición de Smith
A diferencia de la forma normal de Jordan, se garantiza que la forma normal de Smith estará sobre el mismo campo que la matriz original. En lugar de calcular los valores propios y representarlos con una matriz diagonal de bloque, la descomposición de Smith calcula los divisores elementales de la matriz (que es un tema demasiado complicado para esta publicación), los coloca en una matriz diagonal
D
y calcula dos matrices con unidad determinanteU
yV
tal queD = U*A*V
(dondeA
está la matriz original). Desde el determinante del producto de matrices es igual al producto de los determinantes de las matrices (det(A*B*...) = det(A)*det(B)*...
), yU
yV
se definen para tener determinantes de la unidad,det(D) = det(A)
. El determinante de una matriz diagonal es simplemente el producto de los elementos en la diagonal.Expansión de Laplace, 109 bytes
Esto realiza la expansión de Laplace a lo largo de la primera fila, utilizando un enfoque recursivo.
det([[a]]) = a
se usa para el caso base. Debería ser más corto de usardet([[]]) = 1
para el caso base, pero mi intento en esa implementación tenía un error que aún no he podido rastrear.Fórmula de Leibniz, 100 bytes
Esto implementa directamente la fórmula de Leibniz. Para una explicación mucho mejor de la fórmula y por qué funciona de lo que posiblemente podría escribir, vea esta excelente respuesta .
Parte real de
e^(Tr(ln(M)))
48 bytesEsta función devuelve expresiones simbólicas. Para obtener una aproximación numérica, llame
n(result)
antes de imprimir.Este es un enfoque que no he visto a nadie usar todavía. Voy a dar una explicación más larga y más detallada de esta.
Dejar
A
ser una matriz cuadrada sobre los reales. Por definición, el determinante deA
es igual al producto de los valores propios deA
. La traza deA
es igual a la suma deA
los valores propios. Para los números realesr_1
yr_2
,exp(r_1) * exp(r_2) = exp(r_1 + r_2)
. Dado que la función exponencial de la matriz se define como análoga a la función exponencial escalar (especialmente en la identidad anterior), y la exponencial de la matriz se puede calcular diagonalizando la matriz y aplicando la función exponencial escalar a los valores propios en la diagonal, podemos decirdet(exp(A)) = exp(trace(A))
(el producto deexp(λ)
para cada valor propioλ
deA
es igual a la suma de los valores propios deexp(A)
). Por lo tanto, si podemos encontrar una matrizL
tal queexp(L) = A
, podemos calculardet(A) = exp(trace(L))
.Podemos encontrar dicha matriz
L
mediante la computaciónlog(A)
. El logaritmo de la matriz se puede calcular de la misma manera que la matriz exponencial: forma una matriz diagonal cuadrada aplicando la función de logaritmo escalar a cada valor propio deA
(es por eso que restringimosA
a los reales). Como solo nos preocupamos por el rastro deL
, podemos omitir la construcción y simplemente sumar directamente los exponenciales de los valores propios. Los valores propios pueden ser complejos, incluso si la matriz no está sobre el anillo complejo, por lo que tomamos la parte real de la suma.fuente
real(prod(m.eigenvalues()))
golf.Java 8,
266261259258 bytesMira mamá, no hay complementos ... porque Java no tiene ninguno ...>.>
-7 bytes gracias a @ceilingcat .
Explicación:
Pruébalo aquí (Solo el último caso de prueba es demasiado grande para caber en un
long
tamaño de 2 63 -1.)fuente
JavaScript (ES6), 91
Laplace recursiva
Menos golf
Prueba
fuente
Python 2 + numpy , 29 bytes
Pruébalo en línea!
fuente
Julia , 3 bytes
Pruébalo en línea!
fuente
Pari / GP , 6 bytes
Pruébalo en línea!
fuente
Java (OpenJDK 8) ,
195 192177 bytesPruébalo en línea!
Como muchas otras respuestas, esto también usa la fórmula de Laplace. Una versión un poco menos golfizada:
fuente
J , 5 bytes
Pruébalo en línea!
fuente