30/09/2018, 16:49

[Code Review] Tính định thức của ma trận vuông cấp n

Xin chào anh chị, em là new mem ^^ mong các anh chị chỉ giáo cho ạ. hì
Em đang làm bt C đề là: tính định thức của ma trận vuông cấp n bằng cách chuyển thành ma trận tam giác, định thức là tích các phần tử trên đường chéo chính. Phía dưới là code của em, phiền mấy anh chị xem hộ giúp em với ^_^. Cám ơn mọi người nhiều ạ.

#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
int main()
{
    float a[50][50], d=1, t;
    int n, i, j, k;
    printf("nhap cap cua ma tran vuong A
"); scanf("%d",&n);
    //nhap ma tran A
    for(i=0; i<n; i++){
        for(j=0; j<n; j++){
                printf("a[%d][%d]= ", i, j);
                scanf("%f", &a[i][j]);
        }
        printf("
");
    }
    //chuyen ma tran A thanh ma tran tam giac
    /* thuat toan:  - Neu a[k][i]=0 tang k xet phan tu khac
                    - Neu a[k][i]!=0 + Nhan toan bo hang k voi -a[i][i]/a[k][i]
                                     + Lay hang i cong vao hang k
                                     + doi cho hang k va i cho nhau
                                     + nhan toan bo hang k voi -1
                                     + tang k len, xet phan tu tiep theo
    */
    for(i=0; i<n-1; i++){
        for(k=i+1; k<n; k++){
            if(a[k][i]==0) continue;
            if(a[k][i]!=0) {
                    for(j=0; j<n; j++){
                        a[k][j]=-a[k][j]*(a[i][i]/a[k][i]);
                        a[i][j]=a[i][j]+a[k][j];
                        t=a[k][j];
                        a[k][j]=-a[i][j];
                        a[i][j]=t;
                    }
                }
        }
    }
    printf("ma tran tam giac la:
");
    for(i=0; i<n; i++){
        for(j=0; j<n; j++){
            printf("%.2f	",a[i][j]);
        }
        printf("
");
    }
    //tinh dinh thuc
    for(i=0; i<n; i++){
        d=d*a[i][i];
    }
    printf("dinh thuc cua ma tran A= %.2f", d);
    getch();
    return 0;

        }

Nguyễn Minh Dũng viết 18:49 ngày 30/09/2018

Phía dưới là code của em, phiền mấy anh chị xem hộ giúp em với

Xem chạy đúng sai hay code đẹp xấu

Gió viết 18:57 ngày 30/09/2018

thuật toán của bạn bị sai:

for(j=0; j<n; j++){
                        a[k][j]=-a[k][j]*(a[i][i]/a[k][i]);
                        a[i][j]=a[i][j]+a[k][j];
                        t=a[k][j];
                        a[k][j]=-a[i][j];
                        a[i][j]=t;
                    }

=>

float t=a[k][i]/a[i][i]; // he so nhan dong k voi dong i
for(j=i; j<n; j++){
                        a[k][j] -=t*a[i][j];
                    }
  • Nếu a[i][i]==0 phải tìm a[k][i]!=0 rồi swap cho dòng i nếu không sẽ chia cho 0
Daisy viết 18:51 ngày 30/09/2018

Dạ, giả sử em nhập vào ma trận:
0 2 1
1 -1 1
2 3 1
thì không ra được ma trận tam giác

Nguyễn Minh Dũng viết 18:55 ngày 30/09/2018

Tham khảo trả lời của @Gio đi

Daisy viết 18:51 ngày 30/09/2018

Theo em, ngay cái chỗ a[k][i]!=0 , em thực hiện nhân với -a[i][i]/a[k][i] rồi cộng vào hàng i thì đã đảm bảo nó không chia cho 0 rồi

Hoàng Kiên viết 19:04 ngày 30/09/2018

Đây là code Pascal mà em đã làm từ lâu nhưng cũng không động đến nên chưa chuyển sang C được. Các bác tham khảo nhé.

Program DET;
uses    crt,sysutils;
label   loop,start,finish;
var     a:array[1..100,1..100] of real;
        t: double;
        m,n,i,yy,mm,dd:word;
        kt,_loop:byte;
        f:text;
        key:char;
        c:integer;
{  *     c: bien luu cap ma tran
   *     m,n:hang va cot, dung de truot khi nhap va xu ly
   *     i:index, co su dung o vi tri khu 0
   *     kt:kiem tra

                              }
Begin

START:
//Tao file text luu ma tran va dinh thuc da nhap
Decodedate(date,yy,mm,dd);
assign(f,'LogMatrix.txt');
{$I-}
Append(f);
{$I+}
If IOresult<>0 then
        Begin
                Rewrite(f);
                Writeln(f,'This text is created by Matrix.exe');
                Writeln(f,'             +------------------------------------------------+');
                Writeln(f,'             |            Matrix determinant                  |');
                Writeln(f,'             |                                                |');
                Writeln(f,'             |              Dinh thuc ma tran                 |');
                writeln(f,'             +------------------------------------------------+'#10#13);
                Writeln(f);
                Writeln(f,dd,'/',mm,'/',yy,'  ',TimeToStr(time));
                Writeln(f);
        End
Else
Begin
        Writeln(f,'====================================================');
        Writeln(f);
        Writeln(f,dd,'/',mm,'/',yy,'  ',TimeToStr(time));
        Writeln(f);
End;
//Nhap cap ma tran
Clrscr;
_loop:=0;
Writeln('             +------------------------------------------------+');
Writeln('             |             Matrix determinant                 | Press Ctrl+C');
Writeln('             |                                                | to exit');
Writeln('             |              Dinh thuc ma tran                 |');
writeln('             +------------------------------------------------+'#10#13);
Write('                             Nhap cap Ma tran: ');
Readln(c);
If c<0 then
        begin
           writeln;
           writeln('O^ Mai Buoi?. Di ho?i CAVE xem co/ ma tra^n ca^p ',c,' ko nhe/ . -_-');
           goto finish;
        end;
If c=0 then
        begin
           writeln;
           writeln('Ma tra^n ca^p "O" .XXX. ma`y tha^y so^ ma`y vua` nha^.p gio^ng ca/i do/ ko??. :D');
           Writeln('Ca/i ma tra^n na`y kho^ng ti/nh duo.c da^u :v :v :v');
           goto finish;
        end;
If c=1 then
        Begin
           writeLN('Dinh thuc cua ma tran cap 1 chinh bang phan tu duy nhat cua no');
           goto finish;
        End;
If c>100 then
        Begin
           writeln;
           writeln('O^ Mai Chuo^i/... phie^n ba?n sau se~ co/ ma tra^.n ca^p ',c,' :v :v :v');
           goto finish;
        End;
{=================================================================}
//*** Nha Ma tran, in ra ma tran vua nhap.***
Writeln;
Writeln('*** Cac luu y khi nhap Ma tran:');
writeln('        +===========================================================+');
Writeln('        |* Cac so trong mot hang cach nhau boi dau cach "space"     |');
Writeln('        |                                                           |');
Writeln('        |* Ket thuc mot hang bang cach go "Enter"                   |');
Writeln('        |                                                           |');
Writeln('        |* Noi dung Ma tran va dinh thuc duoc luu vao LogMatrix.txt |');
Writeln('        |                                                           |');
Writeln('        |* Nhan Ctrl+C de thoat chuong trinh bat ky luc nao         |');
Writeln('        |                                                           |');
Writeln('        |* Cac so nhap thua o 1 hang se duoc day xuong cac vi tri   |');
Writeln('        |  dau cua hang tiep theo                                   |');
writeln('        +===========================================================+');
Writeln;
Writeln('                           +-----------------+');
writeln('                           | Ma Tran cap ',c:3,' |');
Writeln('                           +-----------------+');
For m:=1 to c do
         Begin
                Writeln;
                Write('Hang ',m,' :   ');
                For n:=1 to c do
                        Read(a[m,n]);
         End;
//Clrscr;
//Writeln('So lieu xuat ra:');
Writeln;
Writeln('-------------------------');
for i:=1 to (((c*7)div 2)-5)do
        Begin
                write(' ');
                write(f,' ');
        End;
Begin
        Writeln('Ma tran cap ',c);
        Writeln(f,'Ma tran cap ',c);
End;
Write('+-');for i:=1 to (7*c) do write(' ');writeln('-+');
Write(f,'+-');for i:=1 to (7*c) do write(f,' ');writeln(f,'-+');
For m:=1 to c do
        Begin
                Write('|');Write(f,'|');
                For n:=1 to c do
                        Begin
                                write(a[m,n]:7:2);
                                write(f,a[m,n]:7:2);
                        end;
                Writeln('  |'); Write('|'); for i:=1 to (c*7+2) do write(' ');writeln('|');
                Writeln(f,'  |'); Write(f,'|'); for i:=1 to (c*7+2) do write(f,' ');writeln(f,'|');
              //  Writeln('----+----+----+-----');
        end;
Write('+-');for i:=1 to (7*c) do write(' ');writeln('-+'#10#13);
Write(f,'+-');for i:=1 to (7*c) do write(f,' ');writeln(f,'-+'#10#13);
{==================================================================}
//Khu so 0 o duong cheo chinh.
LOOP:  {Dat nhan danh dau}
_loop:=_loop+1;
If _loop=200 then
        BEGIN
                WriteLN('Loop failure. Please contact to the Programer.');
                Write('Press any key to exit');
                Exit;
        End;
kt:=1; {bien kiem tra xem Ma tran co phan tu 0 hay ko,
        neu co kiem tra xem co khu duoc theo hang hay ko,
        Co tra ve 1, ko tra ve 0}
For i:=1 to c do
        If a[i,i]=0 then
                Begin
                        n:=0;
                        kt:=0;
                        Repeat
                                n:=n+1;
                                if a[i,n]<>0 then
                                        Begin
                                                kt:=1;
                                                For m:=1 to c do
                                                   a[m,i]:=a[m,i]+a[m,n];
                                        End;
                        Until ((kt=1) or (n=c));
                end;
//Dung thuat toan kien tra 1 phan tu o tren duong cheo cua Ma tran co bang 0
//hay ko. Neu no bang 0, tim cac phan tu trong hang tuong ung voi phan tu do
//xem co phan tu nao khac 0 hay ko, neu co, cong cot cua phan tu tim duoc vao
//cot cua phan tu nam tren truc chinh, cho kt=1. Neu khong tim duoc phan tu
//nao thi gan cho kt=0 (bien kiem tra de suy ra DetA=0 neu co mot hang ma tran
//bang 0

{==================================================================}
//in ra Ma tran da khu so 0 o duong cheo chinh
{
If kt=1 then
BEGIN
Writeln('Ma tran sau khi khu 0 o duong cheo chinh:');
Writeln('------------------------------------------');
Writeln;
For m:=1 to c do
        Begin
                For n:=1 to c do
                        write(a[m,n]:7:2);
                Writeln;
                Writeln;
              //  Writeln('----+----+----+-----');
        end;
Writeln('------------------------------------------'#10#13);
END; }

{==================================================================}

//*** Xu ly Ma tran. ***
If kt=1 then
For i:=1 to c do
        For m:=i+1 to c do
                Begin
                        IF a[i,i]<>0 then
                                begin
                                      t:=(-a[m,i]/a[i,i]);
                                      For n:=i to c do
                                      a[m,n]:=a[m,n]+a[i,n]*t;
                                      If a[m,m]=0 then goto loop;
                                end;
                End;
//Muc dich dua ma tran ve tam giac
//Kiem tra kt=1 thi thuc hien buoc nay de tranh truong hop chi cho 0
//Cho i lap tu 1 -> c de chay phan tu tren truc chinh a[i,i]
//Cho m lap tu i+1 -> c de xu ly hang thu (i+1->c)
//Tinh t=(-a[m,i]/a[i,i]) de tim ra so cong vao lam so hang dau cua hang ma
//tran bang 0.

{===================================================================}
//In ra ma tran da dua ve dang tam giac
{
If kt=1 then
        BEGIN
                Writeln('Ma tran da dua ve tam giac: ');
                Writeln('------------------------------');
                For m:=1 to c do
                    Begin
                        For n:=1 to c do
                                write(a[m,n]:7:2);
                                Writeln;
                                Writeln;
                    End;
                 Writeln('------------------------------'#10#13);
        END;     }
{====================================================================}
//Tinh dinh thuc bang cach nhan cac phan tu cheo

If kt=1 then    {kt=1, ma tran da qua cac buoc tren}
    BEGIN
        t:=1;
        For i:=1 to c do
                t:=t*a[i,i];
    End
Else t:=0; {Neu kt=0 thi DetA=0}

{====================================================================}
Write('DetA= ',t:1:4); //In ra dinh thuc
Writeln(f,'DetA= ',t:1:4);
Readln;
FINISH:
Close(f);
Writeln(#10#13#10#13'--------------------------------');
Writeln(#10#13'Press "E" to exit, any key to continue . . .');
key:=readkey;
If (key<>'E')and(key<>'e') then goto start;
End.
Bài liên quan
0