我在FORTRAN中为共轭梯度法编写了一个代码...有一个错误,我无法在工作数小时后解决它! 附加的代码是执行CGR的子程序,它是我的主程序的一部分,由2个函数和其他子程序组成。
! (C_F2,C2 ,C1 ,C_Fold,IG ,JG ,dCnew,converged)
SUBROUTINE gcr_Mfree(F2 ,Cnew,Cold,C_Fold,IGG,JGG,x ,converged)
!**** FUNCTIONS TO BE SOLVED ****
! Generalized Conjugate Residual Algorithm
! Solves M*x=b (J*dx=-F)
! Use somemodule
! Arguments declarations
IMPLICIT REAL*8 (A-H,O-Z)
INTEGER :: IGG,JGG
real*8, dimension(:), ALLOCATABLE :: x
real*8, intent(out) :: converged !<
REAL*8, DIMENSION(:,:), ALLOCATABLE :: F2,F22,Cnew,Cold,C_Fold,p,Mp
! Variable declarations
real*8 :: alpha2,tol
real*8, DIMENSION(:), ALLOCATABLE :: r,b,Mr,F2V,F22V,CnewV,ColdV,C_FoldV
integer :: i,j,maxiter,AllocateStatus,normr
MASK = SIZE(F2)
ALLOCATE(F2V(1:MASK))
ALLOCATE(CnewV(1:MASK))
ALLOCATE(ColdV(1:MASK))
ALLOCATE(C_FoldV(1:MASK))
!*********** RESHAPING MATRICES TO VECTORS.........
F2V = RESHAPE(F2 ,(/MASK/))
CnewV = RESHAPE(Cnew,(/MASK/))
ColdV = RESHAPE(Cold,(/MASK/))
C_FoldV = RESHAPE(C_Fold,(/MASK/))
b = -F2V !(why minus?)
tol = 5.E-2
alpha2 = 1e-6 ! alpha2 is the epsilon in the report!
maxiter = size(b)
DEALLOCATE(x)
ALLOCATE(x(1:maxiter))
x = 0.0D0 !GUIdE: ""m2f: x = zeros(maxiter,1)""
r = b ! we need this when calculating r_new
! normr(1) = norm2(r) !!!! Norm
DO iter=1,maxiter
!Get preliminary search direction
DO i=1,iter
p(:,i) = r
ENDDO
! Approximate the Jacobian(M) residual product
CnewV = CnewV + alpha2*r
Cnew = RESHAPE(CnewV,(/IGG,JGG/))
F22 = CNF2(Cnew,Cold,Fold,DT)
F22V= RESHAPE(F22V,(/MASK/))
Mr = (1/alpha2)*(F22V-F2V) !GUIDE: (The apporximated Jacobian matrix)
DO i=1,iter
Mp(:,i) = Mr
ENDDO
!! Orthogonalize search direction
do j=1,iter-1
!m2f: p(:,iter) = p(:,iter) - Mp(:,j)'* Mp(:,iter) * p(:,j)
p(:,iter) = p(:,iter) - Mp(j,:) * Mp(:,iter) * p(:,j)
!m2f: Mp(:,iter) = Mp(:,iter) -Mp(:,j)'* Mp(:,iter) * Mp(:,j)
Mp(:,iter) = Mp(:,iter) -Mp(j,:) * Mp(:,iter) * Mp(:,j)
end do
!norm(Mp(:,iter))
!Normalize search direction
p(:,iter) = p(:,iter) / (norm2(Mp(:,iter)))
Mp(:,iter) = Mp(:,iter) / (norm2(Mp(:,iter)))
!Update solution and residual
alpha2 = r * Mp(:,iter) / (Mp(iter,:)) * (Mp(:,iter)))
x = x + alpha2 * p(:,iter)
r = r - alpha2 * Mp(:,iter) ! where is the *(Cnew - C)?
!Check convergence
!!!! normr=norm2(r) !!!! norm
!fprintf('norm(r) = !g iter = !gNewLine',normr,iter+1);
if (normr < tol) then
!fprintf('GCR Converged, iter = !gNewLine',iter+1);
converged=1
exit
end if
END DO !for loop
if (normr > tol) then
write(*,*) 'GCR SOLUTION DID NOT CONVERGE!'
converged=0
end if
RETURN
END subroutine gcr_Mfree
我正在单独编译子程序以解决所有问题。我解决了其他错误,但我无法解决这个问题。
gfortran -Wall -c "gcr_Mfree.f95" (in directory: /home/vahid/Dropbox/To Move folder/Geany)
gcr_Mfree.f95:85.34:
alpha2 = r * Mp(:,iter) / (Mp(iter,:)) * (Mp(:,iter)))
1
Error: Invalid character in name at (1)
Compilation failed.
另一方面,我想知道,如何验证数组元素和形状?特别是我在DO循环中使用(:,iter)的地方。我的意思是,数组在每次迭代时都会将形式向量转换为矩阵,并且矩阵的大小在每次迭代时都会变大。 我知道我可以在编译后在显示器上打印它。我想知道数组的形状/元素,以确保我的方向正确。
答案 0 :(得分:1)
正如casey评论的那样,这解决了你的问题,你的代码因为额外的右括号而出错。不过,说一件事作为答案可能会有所帮助。
你从gfortran得到的错误信息作为诊断信息似乎毫无帮助。查看代码的简化版本(没有完整的声明等)
real, dimension(10,10) :: Mp
alpha2 = r * Mp(:,iter) / (Mp(iter,:)) * (Mp(:,iter)))
end
并编译。使用gfortran 4.9,我收到了类似的消息:
alpha2 = r * Mp(:,iter) / (Mp(iter,:)) * (Mp(:,iter)))
1
Error: Invalid character in name at (1)
相反,使用ifort我得到了更多有用的
error #5276: Unbalanced parentheses
alpha2 = r * Mp(:,iter) / (Mp(iter,:)) * (Mp(:,iter)))
-------------------------------------------------------^