code 33016 ; procedure RK4A(X, XA, B, Y, YA, FXY, E, D, FI, XDIR, POS); value FI, XDIR, POS; boolean FI, XDIR, POS; real X, XA, B, Y, YA, FXY; array E, D; begin integer I; boolean IV, FIRST, FIR, REJ; real K0, K1, K2, K3, K4, K5, FHM, ABSH, DISCR, S, XL, COND0, S1, COND1, YL, HMIN, H, ZL, TOL, HL, MU, MU1; array E1[1:2]; procedure RKSTEP(X, XL, H, Y, YL, ZL, FXY, D); value XL, YL, ZL, H; real X, XL, H, Y, YL, ZL, FXY; integer D; begin if D = 2 then goto INTEGRATE; if D = 3 then begin X:= XL; Y:= YL; K0:= FXY * H end else if D = 1 then K0:= ZL * H else K0:= K0 * MU; X:= XL + H / 4.5; Y:= YL + K0 / 4.5; K1:= FXY * H; X:= XL + H / 3; Y:= YL + (K0 + K1 * 3) / 12; K2:= FXY * H; X:= XL + H * .5; Y:= YL + (K0 + K2 * 3) / 8; K3:= H * FXY; X:= XL + H * .8; Y:= YL + (K0 * 53 - K1 * 135 + K2 * 126 + K3 * 56) / 125; K4:= FXY * H; if D <= 1 then begin X:= XL + H; Y:= YL + (K0 * 133 - K1 * 378 + K2 * 276 + K3 * 112 + K4 * 25) / 168; K5:= FXY * H; DISCR:= ABS(K0 * 21 - K2 * 162 + K3 * 224 - K4 * 125 + K5 * 42) / 14; goto END end; INTEGRATE: X:= XL + H; Y:= YL + ( - K0 * 63 + K1 * 189 - K2 * 36 - K3 * 112 + K4 * 50) / 28; K5:= FXY * H; Y:= YL + (K0 * 35 + K2 * 162 + K4 * 125 + K5 * 14) / 336; END: real procedure FZERO; begin if IV then begin if S = XL then FZERO:= COND0 else if S = S1 then FZERO:= COND1 else begin RKSTEP(X, XL, S - XL, Y, YL, ZL, FXY, 3); FZERO:= B end end else begin if S = YL then FZERO:= COND0 else if S = S1 then FZERO:= COND1 else begin RKSTEP(Y, YL, S - YL, X, XL, ZL, 1 / FXY, 3); FZERO:= B end end end FZERO; if FI then begin D[3]:= XA; D[4]:= YA; D[0]:= 1 end; D[1]:= 0; X:= XL:= D[3]; Y:= YL:= D[4]; IV:= D[0] > 0; FIRST:= FIR:= true; HMIN:= E[0] + E[1]; H:= E[2] + E[3]; if H < HMIN then HMIN:= H; CHANGE: ZL:= FXY; if ABS(ZL) <= 1 then begin if not IV then begin D[2]:= H:= H / ZL; D[0]:= 1; IV:= FIRST:= true end; if FIR then goto A; I:= 1; goto AGAIN end else begin if IV then begin if not FIR then D[2]:= H:= H * ZL; D[0]:= - 1; IV:= false; FIRST:= true end; if FIR then begin H:= E[0] + E[1]; A: if (if FI then (if IV eqv XDIR then H else H * ZL) < 0 eqv POS else H * D[2] < 0) then H:= - H end; I:= 1 AGAIN: ABSH:= ABS(H); if ABSH < HMIN then begin H:= SIGN(H) * HMIN; ABSH:= HMIN end; if IV then begin RKSTEP(X, XL, H, Y, YL, ZL, FXY, I); TOL:= E[2] * ABS(K0) + E[3] * ABSH end else begin RKSTEP(Y, YL, H, X, XL, 1 / ZL, 1 / FXY, I); TOL:= E[0] * ABS(K0) + E[1] * ABSH end; REJ:= DISCR > TOL; MU:= TOL / (TOL + DISCR) + .45; if REJ then begin if ABSH <= HMIN then begin if IV then begin X:= XL + H; Y:= YL + K0 end else begin X:= XL + K0; Y:= YL + H end; D[1]:= D[1] + 1; FIRST:= true; goto NEXT end; H:= H * MU; I:= 0; goto AGAIN end REJ; if FIRST then begin FIRST:= FIR; HL:= H; H:= MU * H; goto ACCEPT end; FHM:= MU * H / HL + MU - MU1; HL:= H; H:= FHM * H; ACCEPT: if IV then RKSTEP(X, XL, HL, Y, YL, ZL, FXY, 2) else RKSTEP(Y, YL, HL, X, XL, ZL, 1 / FXY, 2); MU1:= MU; NEXT: if FIR then begin FIR:= false; COND0:= B; if not (FI or REJ) then H:= D[2] end else begin D[2]:= H; COND1:= B; if COND0 * COND1 <= 0 then goto ZERO; COND0:= COND1 end; D[3]:= XL:= X; D[4]:= YL:= Y; goto CHANGE; ZERO: E1[1]:= E[4]; E1[2]:= E[5]; S1:= if IV then X else Y; S:= if IV then XL else YL ; ZEROIN(S,S1,FZERO,ABS(E1[1]*S)+ABS(E1[2])) ; S1:= if IV then X else Y ; if IV then RKSTEP(X, XL, S - XL, Y, YL, ZL, FXY, 3) else RKSTEP(Y, YL, S - YL, X, XL, ZL, 1 / FXY, 3); D[3]:= X; D[4]:= Y end RK4A; eop