解决二次方程但得到奇怪的错误

时间:2010-04-06 20:32:21

标签: fortran gfortran

我在Fortran尝试我的第一个程序,试图解决二次方程。我有双重和三重检查我的代码,并没有看到任何错误。我不断收到“(1)处名称中的无效字符”和“(1)处的不可分类声明”。代码有什么问题?

! This program solves quadratic equations
! of the form ax^2 + bx + c = 0.
! Record:
! Name:             Date:     Notes:
! Damon Robles      4/3/10    Original Code

PROGRAM quad_solv
IMPLICIT NONE

! Variables
REAL :: a, b, c
REAL :: discrim, root1, root2,    
COMPLEX :: comp1, comp2
CHARACTER(len=1) :: correct 

! Prompt user for coefficients.
WRITE(*,*) "This program solves quadratic equations "
WRITE(*,*) "of the form ax^2 + bx + c = 0. "
WRITE(*,*) "Please enter the coefficients a, b, and "
WRITE(*,*) "c, separated by commas:"
READ(*,*) a, b, c
WRITE(*,*) "Is this correct: a = ", a, " b = ", b
WRITE(*,*) " c = ", c, " [Y/N]? "
READ(*,*) correct
IF correct = N STOP
IF correct = Y THEN

! Definition
discrim = b**2 - 4*a*c

! Calculations
IF discrim > 0 THEN
root1 = (-b + sqrt(discrim))/(2*a)
root2 = (-b - sqrt(discrim))/(2*a)
WRITE(*,*) "This equation has two real roots. "
WRITE(*,*) "x1 = ", root1
WRITE(*,*) "x2 = ", root2
IF discrim = 0 THEN
root1 = -b/(2*a)
WRITE(*,*) "This equation has a double root. "
WRITE(*,*) "x1 = ", root1
IF discrim < 0 THEN
comp1 = (-b + sqrt(discrim))/(2*a)
comp2 = (-b - sqrt(discrim))/(2*a)
WRITE(*,*) "x1 = ", comp1
WRITE(*,*) "x2 = ", comp2

PROGRAM END quad_solv

4 个答案:

答案 0 :(得分:2)

关于如何循环回到重做输入的附加问题 - 演示Fortran的循环特征的示例程序&gt; = 90.循环显然是无限的 - 退出由IF语句控制退出循环并使循环有限。还显示了循环控件,如果遇到无效输入则使用该控件,否则会导致程序崩溃。 (例如,键入“A”作为第一个读取的输入,而不是数字。)在这种情况下,iostat变量获取非零值,IF语句激活循环,​​其余的DO循环是跳过,以便循环重新循环。

program test_readdata

real :: a, b, c
integer :: ReturnCode
character (len=1) :: correct

ReadData: do

   write (*, '( "This program solves quadratic equations of the form ax^2 + bx + c = 0. " )' ) 
   write (*, '( "Please enter the coefficients a, b, and c, separated by commas: " )', advance='no' )
   read (*,*, iostat=ReturnCode) a, b, c
   if ( ReturnCode /= 0 ) cycle ReadData
   write (*,*) "Is this correct: a = ", a, " b = ", b, " c = ", c
   write (*, '( "Enter Y or N: " )', advance='no' )
   read (*,*, iostat=ReturnCode) correct
   if ( ReturnCode /= 0 ) cycle ReadData
   if ( correct == 'Y'  .or.  correct == 'y' )  exit ReadData

end do ReadData

stop

end program test_readdata

我的书推荐: Fortran 95/2003由Metcalf,Reid和Cohen解释

答案 1 :(得分:1)

我注意到你的代码首先注意到程序结束时的语法错误。

END

应该在程序之前

您的编辑器是否突出显示您的语法错误?

您可以非常便宜地获得ELF 90的学生版本,这是一个很好的起点。然后,我将使用Visual Studio和算法流程图生成器升级到Lahey ELF 95,该生成器对颜色传递的路径进行颜色编码。

答案 2 :(得分:0)

这么多错误......似乎你不知道Fortran基础......

最小修正

! This program solves quadratic equations
! of the form ax^2 + bx + c = 0.
! Record:
! Name:             Date:     Notes:
! Damon Robles      4/3/10    Original Code

PROGRAM quad_solv

  IMPLICIT NONE

  ! Variables
  REAL :: a, b, c
  REAL :: discrim, root1, root2    
  COMPLEX :: comp1, comp2
  CHARACTER(len=1) :: correct 

  ! Prompt user for coefficients.
  WRITE(*,*) "This program solves quadratic equations "
  WRITE(*,*) "of the form ax^2 + bx + c = 0. "
  WRITE(*,*) "Please enter the coefficients a, b, and "
  WRITE(*,*) "c, separated by commas:"
  READ(*,*) a, b, c
  WRITE(*,*) "Is this correct: a = ", a, " b = ", b
  WRITE(*,*) " c = ", c, " [Y/N]? "
  READ(*,*) correct

  IF (correct == 'N') STOP

  IF (correct == 'Y') THEN

    ! Definition
    discrim = b**2 - 4*a*c

    ! Calculations
    IF (discrim > 0) THEN
      root1 = (-b + sqrt(discrim))/(2*a)
      root2 = (-b - sqrt(discrim))/(2*a)
      WRITE(*,*) "This equation has two real roots. "
      WRITE(*,*) "x1 = ", root1
      WRITE(*,*) "x2 = ", root2
    ELSEIF (discrim == 0) THEN
      root1 = -b/(2*a)
      WRITE(*,*) "This equation has a double root. "
      WRITE(*,*) "x1 = ", root1
    ELSE
      comp1 = (-b + sqrt(discrim))/(2*a)
      comp2 = (-b - sqrt(discrim))/(2*a)
      WRITE(*,*) "x1 = ", comp1
      WRITE(*,*) "x2 = ", comp2
    END IF

  END IF  

END PROGRAM quad_solv

P.S。我没有检查正确性。 P.P.S.始终缩进代码以使其可读并且不使用STOP语句。每个程序(或子程序)应该有一个入口和一个出口。 STOP的唯一正确位置恰好在END PROGRAM语句之前,它是多余的。所以不要使用STOP。

答案 3 :(得分:0)

一些变化:正确的IF语法;在适当的时候,常数是实数而不是整数:

IF (CORRECT == "N" ) stop
if ( discrim > 0.0 ) then

在其他地方申请,你应该非常接近。祝你好运。

测试具有精确值的浮点数可能是一种不好的算法。如果舍入误差使得disrim的值为1.0E-30,那么当完美算术将值设为零并指示双根时会怎样?