lapack routin zheev的危险行为

时间:2018-07-13 12:50:32

标签: matrix fortran lapack eigenvalue

在使用lapack例程TriggerDagRunOperator时,我偶然发现了一个奇怪的行为。我不明白两个问题

1)我的一个全局变量似乎被zheev()覆盖了。以下小程序显示了它:

[与zheev()一起编译]

gfortran -o test test.f90 -llapack -lblas

输出为

program test    
implicit none

integer, parameter :: dp = 8
integer, parameter :: dim = 3

integer :: l

real(dp), parameter :: kmin = -0.03_dp
real(dp), parameter :: kmax = 0.03_dp
integer, parameter  :: steps = 100
real(dp) :: stepD = (kmax - kmin)/real(steps)
complex(dp) :: matrix(dim,dim)=0.

integer :: info
integer :: rwork=3*dim-2, lwork, lwmax=100
real(dp) :: evals(dim) 
complex(dp) :: work(3*dim-2)

lwork=-1
call zheev('N','U',size(matrix,1), matrix, dim, evals, work, lwork, &
            rwork, info) 
lwork = min( lwmax, int( work(1) ))

do l = 0, 3
    write(*,*) stepD
    call zheev('N', 'U', size(matrix,1), matrix, dim, evals, work, &
    lwork, rwork, info) 
    write(*,*) stepD
end do

end program test

这可以通过将stepD设置为参数来解决。但是我不了解这种行为。越来越奇怪了:

2)将定义中的5.9999999999999995E-004 0.0000000000000000 0.0000000000000000 0.0000000000000000 0.0000000000000000 0.0000000000000000 0.0000000000000000 0.0000000000000000 设置为某个值,例如

lwork

(只需更改上面的相应行) 给出以下结果:

integer :: rwork=3*dim-2, lwork=10, lwmax=100

这怎么可能发生?将 5.9999999999999995E-004 5.9999991208314896E-004 5.9999991208314896E-004 5.9999991208314896E-004 5.9999991208314896E-004 5.9999991208314896E-004 5.9999991208314896E-004 5.9999991208314896E-004 设置为10应该无效,因为稍后将其设置为-1。一个重要的概念是:如果删除了

lwork

代码工作正常。

1 个答案:

答案 0 :(得分:3)

摘自zheev(http://www.netlib.org/lapack/explore-html/df/d9a/group__complex16_h_eeigen_gaf23fb5b3ae38072ef4890ba43d5cfea2.html#gaf23fb5b3ae38072ef4890ba43d5cfea2)的文档:

subroutine zheev    (   character   JOBZ,
        character   UPLO,
        integer     N,
        complex*16, dimension( lda, * )     A,
        integer     LDA,
        double precision, dimension( * )    W,
        complex*16, dimension( * )      WORK,
        integer     LWORK,
        double precision, dimension( * )    RWORK,
        integer     INFO 
    )   

在这里我们看到RWORK是双精度类型的数组,但是在提供的代码rwork中是标量整数