Fortran矩陣求逆(復(fù)矩陣、實(shí)矩陣)

ZuoZhihua
哈爾濱工程大學(xué) 船舶工程學(xué)院
2020/8/13 星期四 午 永新 ThinkPad E485 Elementary os 5.0
QQ:1325686572

1 源碼

module operator_i

    interface operator(.i.) !!// 自定義重載矩陣求逆操作符
    module procedure brinv !!// 實(shí)矩陣求逆
    module procedure bcinv !!// 復(fù)矩陣求逆
    end interface

contains

!!// 實(shí)矩陣求逆核心代碼 trans from 徐士良《Fortran常用算法集》
!!// 作者:zuozhihua 時(shí)間:2020/8/18 地點(diǎn):江西
function brinv(re) result(r)

    real*8,intent(in) :: re(:,:) !!// 原矩陣
    real*8 :: r(size(re,1),size(re,1)) !!// 逆矩陣
    integer*4 :: flag,n !!// flag判斷奇異性额划;n是矩陣維度
    real*8 :: t,d !!// 中間變量
    integer*4 :: is(size(re,1)),js(size(re,1)) !!// 中間變量

    n=size(re,1) !!// 獲取矩陣維度
    r=re !!// 復(fù)制值
    flag=1
    do k=1,n
        d=0.0
        do i=k,n
            do j=k,n
                if (abs(r(i,j)).gt.d) then
                    d=abs(r(i,j))
                    is(k)=i
                    js(k)=j
                end if
            end do
        end do
        if (d+1.0.eq.1.0) then
            flag=0
            write(*,*) "flag=0,實(shí)矩陣奇異踊兜!" 
            return !!// 矩陣奇異,退出逆矩陣求解
        end if
        do j=1,n
            t=r(k,j)
            r(k,j)=r(is(k),j)
            r(is(k),j)=t
        end do
        do i=1,n
            t=r(i,k)
            r(i,k)=r(i,js(k))
            r(i,js(k))=t
        end do
        r(k,k)=1/r(k,k)
        do j=1,n
            if (j.ne.k) r(k,j)=r(k,j)*r(k,k)
        end do
        do i=1,n
            if (i.ne.k) then
                do j=1,n
                    if (j.ne.k) r(i,j)=r(i,j)-r(i,k)*r(k,j)
                end do
            end if
        end do
        do i=1,n
            if (i.ne.k) r(i,k)=-r(i,k)*r(k,k)
        end do
    end do
    do k=n,1,-1
        do j=1,n
            t=r(k,j)
            r(k,j)=r(js(k),j)
            r(js(k),j)=t
        end do
        do i=1,n
            t=r(i,k)
            r(i,k)=r(i,is(k))
            r(i,is(k))=t
        end do
    end do
end function
!!// 復(fù)矩陣求逆核心代碼 trans from 徐士良《Fortran常用算法集》
!!// 作者:zuozhihua 時(shí)間:2020/8/10 地點(diǎn):江西
function bcinv(cpx)
    complex*16,intent(in) :: cpx(:,:) !!// 原矩陣
    complex*16 :: bcinv(size(cpx,1),size(cpx,2)) !!// 逆矩陣
    integer*4 :: flag,n !!// flag判斷奇異性;n是矩陣維度
    real*8 :: ar(size(cpx,1),size(cpx,1)),ai(size(cpx,1),size(cpx,1)) !!// 實(shí)部矩陣ar族吻;虛部矩陣ai
    real*8 :: d,p,t,q,s,b !!// 中間變量
    integer*4 :: is(size(cpx,1)),js(size(cpx,1)) !!// 中間變量

    n=size(cpx,1)
    forall(i=1:n,j=1:n)
        ar(i,j) = real(cpx(i,j));ai(i,j) = imag(cpx(i,j))
    end forall
    flag=1
    do k=1,n
        d=0.0
        do i=k,n
            do j=k,n
                p=ar(i,j)*ar(i,j)+ai(i,j)*ai(i,j)
                if(p.gt.d) then
                    d=p
                    is(k)=i
                    js(k)=j
                end if
            end do
        end do
        if(d+1.0.eq.1.0) then
            flag=0
            write(*,*) "flag=0,復(fù)矩陣奇異!" 
            return !!// 矩陣奇異珠增,退出逆矩陣求解
        end if
        do j=1,n
            t=ar(k,j)
            ar(k,j)=ar(is(k),j)
            ar(is(k),j)=t
            t=ai(k,j)
            ai(k,j)=ai(is(k),j)
            ai(is(k),j)=t
        end do
        do i=1,n
            t=ar(i,k)
            ar(i,k)=ar(i,js(k))
            ar(i,js(k))=t
            t=ai(i,k)
            ai(i,k)=ai(i,js(k))
            ai(i,js(k))=t
        end do
        ar(k,k)=ar(k,k)/d
        ai(k,k)=-ai(k,k)/d
        do j=1,n
            if(j.ne.k) then
                p=ar(k,j)*ar(k,k)
                q=ai(k,j)*ai(k,k)
                s=(ar(k,j)+ai(k,j))*(ar(k,k)+ai(k,k))
                ar(k,j)=p-q
                ai(k,j)=s-p-q
            end if
        end do
        do i=1,n
            if(i.ne.k) then
                do j=1,n
                    if (j.ne.k) then
                        p=ar(k,j)*ar(i,k)
                        q=ai(k,j)*ai(i,k)
                        s=(ar(k,j)+ai(k,j))*(ar(i,k)+ai(i,k))
                        t=p-q
                        b=s-p-q
                        ar(i,j)=ar(i,j)-t
                        ai(i,j)=ai(i,j)-b
                    end if
                end do
            end if
        end do
        do i=1,n
            if (i.ne.k) then
                p=ar(i,k)*ar(k,k)
                q=ai(i,k)*ai(k,k)
                s=(ar(i,k)+ai(i,k))*(ar(k,k)+ai(k,k))
                ar(i,k)=q-p
                ai(i,k)=p+q-s
            end if
        end do
    end do
    do k=n,1,-1
        do j=1,n
            t=ar(k,j)
            ar(k,j)=ar(js(k),j)
            ar(js(k),j)=t
            t=ai(k,j)
            ai(k,j)=ai(js(k),j)
            ai(js(k),j)=t
        end do
        do i=1,n
            t=ar(i,k)
            ar(i,k)=ar(i,is(k))
            ar(i,is(k))=t
            t=ai(i,k)
            ai(i,k)=ai(i,is(k))
            ai(i,is(k))=t
        end do
    end do
    forall(i=1:n,j=1:n)
        bcinv(i,j) = cmplx(ar(i,j),ai(i,j),8)
    end forall

end function
end module

program main

    use operator_i
    implicit none
    real*8 :: r(2,2),ri(2,2)
    integer*4 :: i,j
    complex*16 :: c(4,4),ci(4,4)

    c=reshape((/(0.2368,0.1345),(1.1161,1.2671),(0.1582,-0.2836),(0.1968,0.3576),&
    (0.2471,0.1678),(0.1254,0.2017),(1.1675,-1.1967),(0.2071,-1.2345),&
    (0.2568,0.1825),(0.1397,0.7024),(0.1768,0.3558),(1.2168,2.1185),&
    (1.2671,1.1161),(0.1490,0.2721),(0.1871,-0.2078),(0.2271,0.4773)/),(/4,4/))
    ci=.i.c
    write(*,*) "復(fù)矩陣:"
    write(*,"(8(4x,es10.3))") ((c(i,j),j=1,4),i=1,4)
    write(*,*) "逆矩陣:"
    write(*,"(8(4x,es10.3))") ((ci(i,j),j=1,4),i=1,4)
    write(*,*) "校核:"
    write(*,"(8(4x,es10.3))") matmul(c,ci)

    r=reshape((/1,3,2,4/),(/2,2/))
    ri=.i.r
    write(*,*) "實(shí)矩陣:"
    write(*,"(2(4x,es10.3))") ((r(i,j),j=1,2),i=1,2)
    write(*,*) "逆矩陣:"
    write(*,"(2(4x,es10.3))") ((ri(i,j),j=1,2),i=1,2)
    write(*,*) "校核:"
    write(*,"(2(4x,es10.3))") matmul(r,ri)

end program

2 運(yùn)行

程序運(yùn)行圖.png

參考文獻(xiàn)


[1] 徐士良超歌,F(xiàn)ortran常用算法集。
[2] 白海波蒂教,F(xiàn)ortran程序設(shè)計(jì)權(quán)威指南巍举。
[3] zuozhihua,Fortran復(fù)數(shù)矩陣相乘凝垛。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末懊悯,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子梦皮,更是在濱河造成了極大的恐慌炭分,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,188評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件届氢,死亡現(xiàn)場(chǎng)離奇詭異欠窒,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,464評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門岖妄,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)型将,“玉大人,你說(shuō)我怎么就攤上這事荐虐∑叨担” “怎么了?”我有些...
    開(kāi)封第一講書人閱讀 165,562評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵福扬,是天一觀的道長(zhǎng)腕铸。 經(jīng)常有香客問(wèn)我,道長(zhǎng)铛碑,這世上最難降的妖魔是什么狠裹? 我笑而不...
    開(kāi)封第一講書人閱讀 58,893評(píng)論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮汽烦,結(jié)果婚禮上涛菠,老公的妹妹穿的比我還像新娘。我一直安慰自己撇吞,他們只是感情好俗冻,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,917評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著牍颈,像睡著了一般迄薄。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上煮岁,一...
    開(kāi)封第一講書人閱讀 51,708評(píng)論 1 305
  • 那天讥蔽,我揣著相機(jī)與錄音,去河邊找鬼画机。 笑死勤篮,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的色罚。 我是一名探鬼主播碰缔,決...
    沈念sama閱讀 40,430評(píng)論 3 420
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼戳护!你這毒婦竟也來(lái)了金抡?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書人閱讀 39,342評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤腌且,失蹤者是張志新(化名)和其女友劉穎梗肝,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體铺董,經(jīng)...
    沈念sama閱讀 45,801評(píng)論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡巫击,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,976評(píng)論 3 337
  • 正文 我和宋清朗相戀三年禀晓,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片坝锰。...
    茶點(diǎn)故事閱讀 40,115評(píng)論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡粹懒,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出顷级,到底是詐尸還是另有隱情凫乖,我是刑警寧澤,帶...
    沈念sama閱讀 35,804評(píng)論 5 346
  • 正文 年R本政府宣布弓颈,位于F島的核電站帽芽,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏翔冀。R本人自食惡果不足惜导街,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,458評(píng)論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望纤子。 院中可真熱鬧菊匿,春花似錦、人聲如沸计福。這莊子的主人今日做“春日...
    開(kāi)封第一講書人閱讀 32,008評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)象颖。三九已至,卻和暖如春姆钉,著一層夾襖步出監(jiān)牢的瞬間说订,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書人閱讀 33,135評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工潮瓶, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留陶冷,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,365評(píng)論 3 373
  • 正文 我出身青樓毯辅,卻偏偏與公主長(zhǎng)得像埂伦,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子思恐,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,055評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容