在Fortran中重新启动循环

时间:2017-02-03 14:36:53

标签: algorithm loops fortran fortran90 fortran77

我的算法看起来像这样:

10 WRITE (*,*) "Start"
DO I = 1, 10
WRITE (*,*) "Step"
IF(I .EQ. 5) then 
    go to 10
END IF
END DO

我想在if语句执行时重启循环。但是,我不想使用go,我试过这个:

10 WRITE (*,*) "Start"
DO I = 1, 10
WRITE (*,*) "Step"
IF(I .EQ. 5) then 
    I = 0; CYCLE
END IF
END DO

然后我得到了错误,我无法在循环内重新定义I变量。所以我不确定如何处理这个问题。任何帮助将不胜感激

3 个答案:

答案 0 :(得分:9)

一个概念上简单的解决这个问题的方法是:“我想重复一个循环,直到它完成,哪里有一些中止条件”。

这个“重复直到它完成”是惯用的具有不确定迭代的do构造:

do
  ...  ! Our actions; we exit this outer loop when we are satisfied
end do

[这也可以表达为do-while循环。]

使用内循环:

do
  do i=1,10
     ... ! A conditional statement which aborts the inner loop
     ... ! And some actions
  end do
  ! And once we're complete we exit the outer loop
end do

现在只需处理“中止内部”和“退出外部”。这里cycleexit

outer: do
  print*, 'Start'
  do i=1,10
    print*, 'Step'
    if (...) cycle outer   ! Abort the inner loop
  end do
  exit outer  ! The inner loop completed, so we're done
end do outer

标记外部循环,以便内部循环中的cycle语句可以引用它。如果没有该标签,cycle将循环包含它的最内层循环。

答案 1 :(得分:-1)

在某处可能是一个拼写错误,但在“同时”意义上还有其他一些想法。

即。人们可以调查一些事情。

... USE ISO... etc stuff.
REAL(KIND=C_FLOAT), DIMENSION(10) :: A
LOGICAL(KIND=C_BOOL)              :: Question1 = .TRUE.
LOGICAL(KIND=C_BOOL)              :: Question2 = .TRUE.
INTEGER(KIND=C_INT)               :: Index     = 0
INTEGER(KIND=C_INT)               :: I         = 5

WRITE(*,*)'Enter first index to skip:"
READ(*,*) I

Outer_Loop: DO WHILE (Question1)    ! .eq. .TRUE.

  Inner_Loop:  DO WHILE (Question2) ! .EQV. .TRUE.
    Index = Index + 1
    IF(Index > UBOUND(A,1)) THEN
      Question1 = .FALSE.
      Question2 = .FALSE.
      Exit
    ENDIF
    IF(Index == I) EXIT

    !Whatever like  A(INdex) = something....

  ENDDO Inner_Loop

  IF(Question1) THEN   !We must have more to possibly read or do...
    WRITE(*,*)'Do more? 1=yes, 0=No"
    READ(*,*) I
    IF(I == 1) THEN
      WRITE(*,*)'Enter next index to skip:"
      READ(*,*) I
      Question2 = .TRUE.
  !and one can do a reset of I=0 here, which then becomes I=1 the next time through the inner loop...
    ELSE
      Question1 = .FALSE.
      Question2 = .FALSE.
      EXIT
    ENDIF
  ELSE   !Must have gotten here to exit at the end of array?
    EXIT
  ENDIF
ENDDO Outer_Loop

答案 2 :(得分:-2)

我可以建议解决此问题的方法:使用while循环或递归函数(高度取决于您的实际算法)。我为这两种情况附加了一个示例代码(请记住,使用保存限定符的变量不是最好的想法,通过将变量作为参数传递给函数来做这件事要好得多 - 这里它仅用于简单)

module functions

    implicit none

    integer :: restarted, save = 0
contains

    recursive subroutine restart_loop
        integer :: i

        do i = 1, 10
            print*, i
            if ( i == 5 .and. restarted < 5 ) then
                restarted = restarted + 1
                call restart_loop
                exit
            end if            
        end do        
    end subroutine restart_loop

    subroutine while_loop
        integer :: i = 1

        do while (i <= 10)
            print*, i
            if ( i == 5 .and. restarted < 5 ) then
                i = 1
                restarted = restarted + 1
            end if
            i = i + 1
        end do
    end subroutine while_loop
end module functions

program test_prog
    use functions

    implicit none

    call while_loop
end program test_prog