Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: Kasswed en 11 Enero 2009, 20:53 pm



Título: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: Kasswed en 11 Enero 2009, 20:53 pm
Hola.

A ver si alguien me puede explicar algún algoritmo o darme algún pseudocódigo (por favor nada de álgebra), para calcular en C el determinante de una matriz de orden 'n'.

Muchas gracias.


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: Anibal784 en 12 Enero 2009, 00:56 am
Cómo que nada de álgebra si el determinante de una matriz es de álgebra. Esto es tan sencillo, es sólo cuestión de encontrar la definición, ver un método de cómo calcularla y transformar ese método en el algoritmo en el lenguaje que te gusta.


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: Kasswed en 12 Enero 2009, 01:02 am
Si es muy sencillo.

Bueno comentarios tan útiles como el tuyo se agradecen, se encuentran pocos hoy en día. La verdad es que no había caído en basarme en fórmulas algebraicas para hacer el algoritmo, menos mal que lo has dicho.

Gracias por la ayuda.


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: VirucKingX en 12 Enero 2009, 01:15 am
Si es muy sencillo.

Bueno comentarios tan útiles como el tuyo se agradecen, se encuentran pocos hoy en día. La verdad es que no había caído en basarme en fórmulas algebraicas para hacer el algoritmo, menos mal que lo has dicho.

Gracias por la ayuda.

yo te entiendo, hace algun tiempo tambien intente hacer esto, pero nunca encontre una formula recursiva que funcionara com matrices de orden mayor que 5

Dale una mirada a esto, segun el autor dice que funciona. Pero yo no lo e probado

 
Citar
http://www.elrincondelc.com/nuevorincon/foros/viewtopic.php?t=2837


esop


Chau


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: juancaa en 7 Febrero 2012, 11:49 am
Aunque llego un poco tarde creo que tengo lo que buscais:

http://foro.elhacker.net/programacion_cc/determinante_matriz_de_orden_n-t352910.0.html (http://foro.elhacker.net/programacion_cc/determinante_matriz_de_orden_n-t352910.0.html)


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: Xandrete en 7 Febrero 2012, 16:18 pm
Perdón, sólo quería comentar para decir que me has partido el corazón (en un sentido negativo)...

Citar
por favor nada de álgebra

Me voy a llorar, lo siento  :-(

P.S. Que sepas que un hipopótamo ha muerto por tu culpa, xD


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: BlackZeroX en 8 Febrero 2012, 08:37 am
Me espere unos dias antes de soltar el codigo...

Código
  1.  
  2. #include <stdlib.h>
  3. #include <stdio.h>   //<stdio.h>
  4.  
  5. typedef
  6. struct Matrix
  7. {
  8.    float **lpData;
  9.    unsigned int uiRows;
  10.    unsigned int uiCols;
  11. }
  12. MATRIX, *LPMATRIX;
  13.  
  14. LPMATRIX createMatrix(unsigned int uiRows, unsigned int uiCols)
  15. {
  16.    LPMATRIX lpRet = (LPMATRIX)malloc(sizeof(MATRIX));
  17.    int i = 0;
  18.    lpRet->uiCols = uiCols;
  19.    lpRet->uiRows = uiRows;
  20.    lpRet->lpData = (float**)malloc(sizeof(float*) * lpRet->uiRows);
  21.    for (i = 0; i < lpRet->uiRows; i++)
  22.        lpRet->lpData[i] = (float*)malloc(sizeof(float) * lpRet->uiCols);
  23.    return lpRet;
  24. }
  25.  
  26. void freeMatrix(LPMATRIX lpMatrix)
  27. {
  28.    int i = 0;
  29.    if (!lpMatrix) return;
  30.    for (i = 0; i < lpMatrix->uiRows; i++)
  31.        free(lpMatrix->lpData[i]);
  32.    free(lpMatrix->lpData);
  33.    free(lpMatrix);
  34. }
  35.  
  36. void showMatrix(LPMATRIX lpMatrix)
  37. {
  38.    int i = 0,
  39.        j = 0;
  40.    if (!(lpMatrix || lpMatrix->lpData)) return;
  41.    for (i = 0; i < lpMatrix->uiRows; i++)
  42.    {
  43.        if (lpMatrix->lpData[i])
  44.        {
  45.            for (j = 0; j < lpMatrix->uiCols; j++)
  46.                printf("\t%f", lpMatrix->lpData[i][j]);
  47.            printf("\n");
  48.        }
  49.    }
  50. }
  51.  
  52. int getDeterminant(LPMATRIX lpMatrix, float* lpOutDeterminant)
  53. //  Retorna 0 si todo a ido bien, de lo contrario retorna un numero distinto de 0
  54. {
  55.    float fRet = 0.0f,
  56.          fProduct = 0.0f;
  57.    unsigned int i = 0,
  58.                 j = 0;
  59.    if (!(lpMatrix || lpMatrix->lpData) || (lpMatrix->uiRows < 2) || (lpMatrix->uiCols < 2) || (lpMatrix->uiRows != lpMatrix->uiCols)) return -1;
  60.  
  61.    if (lpMatrix->uiCols == 2)
  62.    {
  63.        if (!(lpMatrix->lpData[0] && lpMatrix->lpData[1])) return -1;
  64.        fRet = lpMatrix->lpData[0][0] * lpMatrix->lpData[1][1] - lpMatrix->lpData[1][0] * lpMatrix->lpData[0][1];
  65.  
  66.    } else {
  67.        for (i = 0; i < lpMatrix->uiRows; i++)
  68.        {
  69.            if (!lpMatrix->lpData[i]) return -1;
  70.            //  Multiplicacion de valores verticales de izquierda a derecha...
  71.            fProduct = 1.0f;
  72.            for (j = 0; j < lpMatrix->uiCols; j++)
  73.                fProduct *= lpMatrix->lpData[(i + j) % lpMatrix->uiCols][j];
  74.            fRet += fProduct;
  75.  
  76.            //  Multiplicacion de valores verticales de derecha a izquierda...
  77.            fProduct = 1.0f;
  78.            for (j = 0; j < lpMatrix->uiCols; j++)
  79.                fProduct *= lpMatrix->lpData[(lpMatrix->uiCols - 1) - ((i + j) % lpMatrix->uiCols)][j];
  80.            fRet -= fProduct;
  81.        }
  82.    }
  83.    if (lpOutDeterminant)
  84.        *lpOutDeterminant = fRet;
  85.  
  86.    return 0;
  87. }
  88.  
  89. int main()
  90. {
  91.    LPMATRIX lpMatrix = createMatrix(3,3);
  92.    float fDeterminant = 0.0;
  93.    int i = 0,
  94.        j = 0;
  95.    for (i = 0; i < lpMatrix->uiRows; i++)
  96.    {
  97.        for (j = 0; j < lpMatrix->uiCols; j++)
  98.        {
  99.            printf("[%d][%d] = ",i, j); fflush(stdout);
  100.            scanf("%f", &lpMatrix->lpData[i][j]);
  101.        }
  102.    }
  103.    fflush(stdout);
  104.    showMatrix(lpMatrix);
  105.    if (getDeterminant(lpMatrix, &fDeterminant) == 0)
  106.        printf("Determinante = %f\n", fDeterminant);
  107.    freeMatrix(lpMatrix);
  108.  
  109.    getchar();
  110.  
  111.    return EXIT_SUCCESS;
  112. }
  113.  
  114.  

Temibles Lunas!¡.


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: do-while en 8 Febrero 2012, 14:56 pm
¡Buenas!

Un metodo sencillo (aunque intuyo que no el mas eficiente) seria diagonailzar la matriz por Gauss y multiplicar los elementos de la diagonal.

Tambien puedes hacer ceros por ejemplo en la primera columna y aplicar la definicion. Te hara falta un algoritmo recursivo que repita el proceso para matrices de menor orden que la dada (hasta llegar a matrices 1x1):

|A| = Suma(desde i = 1 hasta n)(-1)i+j·aij·|Aij|

Donde i es el indice de la fila, j el de una columna prefijada y Aij es la matriz resultante de eliminar de A la fila i y columna j.

La definicion basica de determinanta se realiza ulilizando sumas de productos de permutaciones de los elementos de las filas multiplicando en cada suma por la signatura de la permutacion, pero esto ya es mas complicado de implementar, y el hecho de tener que estar calculando permutaciones hara que el algoritmo sea muy poco eficiente.

Te recomiendo cualquiera de los dos primeros algoritmos. El primero es iterativo y el segundo recursivo.

¡Saludos!


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: Crowsnest en 24 Enero 2013, 13:09 pm
Hola Amigos:

Aunque no este en C++, es facil de traducir.

Aqui os dejo un codigo mio en VB.NET para resolver determinantes de orden n x n

Declaracion de la clase desde programa en VB.NET
Dim clase As SolDet = New SolDet()


LLAMADAS A LA CLASE SolDet (renombrada "clase" en el ejemplo):
        clase.resuelve(test,n, n), ejecuta calculo Matricial
        clase.Calcula(n, n), Devuelve valor determinante

Donde Det es la matriz a calcular yn,n son las dimensiones de la Matriz.
La matriz esta ordenada por filas, ejpl. {{1,2,3,4},{2,1,4,7},.........}


        clase.ver_datos(), devuelve matriz diagonalizada.



Public Class SolDet

    'by  jmlv-Crowsnest
    Public paso(1, 1) As Double


    Public Sub resuelve(ByVal det, ByVal ylim, ByVal xlim)

        If xlim <> ylim Then
            MsgBox("Only squared matrixes allowed")
            Exit Sub
        End If


        ReDim paso(ylim - 1, xlim - 1) ' row-col Number
        Dim x, y As Integer
        Dim f, referencia, operador As Double
        Dim acarreo As Integer

        'det() Reference Matrix
        'paso() Result Matrix

        Array.Copy(det, paso, det.length) 'Build initial result matrix

        For acarreo = 0 To xlim - 2 ' Move row selection pointer for zero making

            referencia = -det(acarreo, acarreo) 'Diagonal reference value

            For y = acarreo + 1 To ylim - 1 'Move along row of column y

                operador = det(y, acarreo) 'Matrix element at the same column than reference

                f = operador / referencia 'Multiplication factor for row Y

                For x = 0 To xlim - 1 'Move and apply f along row

                    paso(y, x) = det(acarreo, x) * f + det(y, x)

                Next

            Next

            'Rebuild reference Matrix.
            Array.Copy(paso, det, paso.Length)
            Array.Copy(det, paso, det.length)

        Next



    End Sub

    Public Function ver_datos() As Array

        Return paso
    End Function

    Public Function Calcula(ByVal ylim, ByVal xlim) As Double
        Dim y As Integer
        Dim prod As Double

        prod = 1

        For y = 0 To ylim - 1

            prod = prod * paso(y, y)

        Next

        Return prod

    End Function


End Class

NOTAS:
Metodo de Gauss, admite cualquier orden n.

Un saludo


Título: Re: [C] Calcular determinante de una matriz de orden 'n'
Publicado por: flony en 24 Enero 2013, 15:37 pm
yo se que hay ganas de ayudar y eso ...pero alguien se fijo la fecha  :¬¬ :¬¬
Citar
Publicado en: Enero 11, 2009, 04:53:58
de todas formas en el transcurso de los días respondo es un lindo desafió ;)