! iqsort -> sorting an integer array (keeping trace of the permutation) ! rqsort -> sorting a real array (keeping trace of the permutation) ! dpqsort -> sorting a double precision array (keeping trace of the permutation) !=============================================================================== !=====[rqsort]================================================================== !=============================================================================== SUBROUTINE rqsort(a, n, t) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. ! SINGLE PRECISION, ALSO CHANGES THE ORDER OF THE ASSOCIATED ARRAY T. IMPLICIT NONE INTEGER, INTENT(IN) :: n REAL, INTENT(INOUT) :: a(n) INTEGER, INTENT(INOUT) :: t(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww REAL :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) ww = t(i) a(i) = a(j) t(i) = t(j) a(j) = w t(j) = ww i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE rqsort !=============================================================================== !=====[iqsort]================================================================== !=============================================================================== SUBROUTINE iqsort(a, n, t) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. ! ALSO CHANGES THE ORDER OF THE ASSOCIATED ARRAY T. IMPLICIT NONE INTEGER, INTENT(IN) :: n INTEGER, INTENT(INOUT) :: a(n) INTEGER, INTENT(INOUT) :: t(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww INTEGER :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) ww = t(i) a(i) = a(j) t(i) = t(j) a(j) = w t(j) = ww i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE iqsort !=============================================================================== !=====[dpqsort]================================================================= !=============================================================================== SUBROUTINE dpqsort(a, n, t) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. ! DOUBLE PRECISION, ALSO CHANGES THE ORDER OF THE ASSOCIATED ARRAY T. IMPLICIT NONE INTEGER, INTENT(IN) :: n REAL*8, INTENT(INOUT) :: a(n) INTEGER, INTENT(INOUT) :: t(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww REAL*8 :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) ww = t(i) a(i) = a(j) t(i) = t(j) a(j) = w t(j) = ww i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE dpqsort !=============================================================================== !=====[rqsort_s]================================================================== !=============================================================================== SUBROUTINE rqsort_s(a, n) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. IMPLICIT NONE INTEGER, INTENT(IN) :: n REAL, INTENT(INOUT) :: a(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww REAL :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) a(i) = a(j) a(j) = w i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE rqsort_s !=============================================================================== !=====[iqsort_s]================================================================ !=============================================================================== SUBROUTINE iqsort_s(a, n) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. IMPLICIT NONE INTEGER, INTENT(IN) :: n INTEGER, INTENT(INOUT) :: a(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww INTEGER :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) a(i) = a(j) a(j) = w i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE iqsort_s !=============================================================================== !=====[dpqsort_s]=============================================================== !=============================================================================== SUBROUTINE dpqsort_s(a, n) ! NON-RECURSIVE STACK VERSION OF QUICKSORT FROM N.WIRTH'S PASCAL ! BOOK, 'ALGORITHMS + DATA STRUCTURES = PROGRAMS'. IMPLICIT NONE INTEGER, INTENT(IN) :: n REAL*8, INTENT(INOUT) :: a(n) ! Local Variables INTEGER :: i, j, k, l, r, s, stackl(15), stackr(15), ww REAL*8 :: w, x s = 1 stackl(1) = 1 stackr(1) = n ! KEEP TAKING THE TOP REQUEST FROM THE STACK UNTIL S = 0. 10 CONTINUE l = stackl(s) r = stackr(s) s = s - 1 ! KEEP SPLITTING A(L), ... , A(R) UNTIL L >= R. 20 CONTINUE i = l j = r k = (l+r) / 2 x = a(k) ! REPEAT UNTIL I > J. DO DO IF (a(i).LT.x) THEN ! Search from lower end i = i + 1 CYCLE ELSE EXIT END IF END DO DO IF (x.LT.a(j)) THEN ! Search from upper end j = j - 1 CYCLE ELSE EXIT END IF END DO IF (i.LE.j) THEN ! Swap positions i & j w = a(i) a(i) = a(j) a(j) = w i = i + 1 j = j - 1 IF (i.GT.j) EXIT ELSE EXIT END IF END DO IF (j-l.GE.r-i) THEN IF (l.LT.j) THEN s = s + 1 stackl(s) = l stackr(s) = j END IF l = i ELSE IF (i.LT.r) THEN s = s + 1 stackl(s) = i stackr(s) = r END IF r = j END IF IF (l.LT.r) GO TO 20 IF (s.NE.0) GO TO 10 RETURN END SUBROUTINE dpqsort_s