{$N+} uses Appendix; const Cy0 : RealType = -0.204; Cya : RealType = 4.1639; Cx0 : RealType = 0.0217; A : RealType = 0.0653; type TNavApp = object(TSampleApp) k, a1,a2,a11,a12,a21,a22, b1,b2,b11,b12,b21,b22, c1,c2,c3,c11,c12, H1,H2, V1,V2, H,V, alfa : RealType; procedure Compute; virtual; function g : RealType; function P : RealType; function q : RealType; function r : RealType; function Func1 : RealType; function Func2 : RealType; function Func3 : RealType; end; function Min(p1,p2,p3 : RealType) : Byte; begin if p1 < p2 then if p1 < p3 then Min := 1 else Min := 3 else if p2 < p3 then Min := 2 else Min := 3 end; { - Min - } procedure Quadr(a,b,c : RealType; var x1,x2 : RealType; var Result : Byte); var d : RealType; begin Result := 0; if abs(a) < eps then begin if abs(b) < eps then Exit; x1 := -c/b; x2 := -c/b; Result := 1 end else begin d := sqr(b)-4*a*c; if d < -eps then Exit; d := sqrt(d); x1 := (-b-d)/(2*a); x2 := (-b+d)/(2*a); Result := 2 end end; { - Quadr - } { TNavApp } {function TNavApp.Arr(i,j : Integer) : PItem; begin Arr := Ptr(Seg(Row[i]^),Ofs(Row[i]^)+(j-1)*SizeOf(TItem)) end; { - Arr - } procedure TNavApp.Compute; var i,j : Integer; S1,S2,S3 : RealType; BufItem, Item : PDirect; procedure Clear(N : Integer); var i : Integer; begin for i := 1 to N do FreeMem(Row[i],(nmax+1)*SizeOf(TItem)); DoneProcess; end; begin inherited Compute; IsCompute := False; DisableCommands([cmGraphic]); if Way <> NIL then begin Item := Way; while Item <> NIL do begin BufItem := Item^.Next; Dispose(Item); Item := BufItem; end; end; New(Way); Way^.Data := 0; Way^.Next := NIL; { Подготовка } k := (HB-HA)/(VB-VA)*nmax/mmax; a11 := sqr(S*Cya)*2*A*(Cx0+3*A*sqr(Cy0)); a12 := sqr(S*Cya); a1 := a11+a12; a21 := -2*A*S*sqr(Cya); a22 := 2*S*Cya; a2 := a21+a22; b11 := 4*sqr(S)*Cy0*Cya*A*(Cx0+A*sqr(Cy0)); b12 := 2*sqr(S)*Cy0*Cya; b1 := b11+b12; b21 := -4*S*Cy0*A*Cya; b22 := 2*S*Cy0; b2 := b21+b22; c11 := sqr(S)*(sqr(Cy0)*2*A*(Cx0+0.5*A*sqr(Cy0))+sqr(Cx0)); c12 := sqr(S*Cy0); c1 := c11+c12; c2 := -2*S*(Cx0+A*sqr(Cy0)); c3 := -sqr(m); InitProcess('Подготовка'); for i := 1 to mmax+1 do begin GetMem(Row[i],(nmax+1)*SizeOf(TItem)); H1 := (HB-HA)*(i-1)/mmax+HA; H2 := (HB-HA)*i/mmax+HA; for j := 1 to nmax+1 do begin V1 := VA+(VB-VA)*(j-1)/nmax; V2 := VA+(VB-VA)*j/nmax; with Arr(i,j)^ do begin if i = mmax+1 then X[2] := Max else X[2] := Func2; if j = nmax+1 then X[1] := Max else X[1] := Func1; if (i = mmax+1) or (j = nmax+1) then X[3] := Max else X[3] := Func3; S := 0; end; end; if not Process(i) then begin Clear(i); Exit; end end; DoneProcess; { Алгоритм } { 1. Определение весов каждого узла } InitProcess('Алгоритм'); for i := mmax+1 downto 2 do with Arr(i-1,nmax+1)^ do begin D := 2; S := Arr(i,nmax+1)^.S+X[D] end; for j := nmax+1 downto 2 do with Arr(mmax+1,j-1)^ do begin D := 1; S := Arr(mmax+1,j)^.S+X[D] end; for i := mmax downto 1 do begin for j := nmax downto 1 do with Arr(i,j)^ do begin S1 := Arr(i,j+1)^.S+X[1]; S2 := Arr(i+1,j)^.S+X[2]; S3 := Arr(i+1,j+1)^.S+X[3]; D := min(S1,S2,S3); S := Arr(i+D div 2,j+D mod 2)^.S+X[D]; if S >= Max then begin Clear(mmax+1); FlightImpossible; Exit; end; end; if not Process(mmax-i) then begin Clear(mmax+1); Exit; end end; Clear(mmax+1); { 2. Заполнение списка направлений оптимального полета } i := 1; j := 1; BufItem := Way; repeat with Arr(i,j)^ do begin New(Item); BufItem^.Next := Item; Item^.Data := D; Item^.Next := NIL; BufItem := Item; i := i+D div 2; j := j+D mod 2; end until (i = mmax+1) and (j = nmax+1); Time := Arr(1,1)^.S; IsCompute := True; EnableCommands([cmGraphic]) end; { - Compute - } function TNavApp.g; begin g := 9.8065-3.055e-6*H end; { - g - } function TNavApp.r; begin r := 1.213-9.7956e-5*H; end; { - r - } function TNavApp.q; begin q := r*sqr(V)/2; end; { - q - } function TNavApp.P; begin if IsPconstant then P := (3*P0)*MaxP/100 else P := (3*(P0-(P0-35000)*H/11000))*MaxP/100; end; { - P - } function TNavApp.Func1; var F : RealType; begin H := H1; V := (V1+V2)/2; alfa := (m*g-Cy0*q*S)/(P+Cya*q*S); F := P-(Cx0+A*sqr(Cy0+Cya*alfa))*q*S; if F < 0 then Func1 := Max else Func1 := m/F*(V2-V1); end; { - Func1 - } function TNavApp.Func2; var aa,bb,cc : RealType; sinf : RealType; x1,x2 : RealType; Result : Byte; begin H := (H1+H2)/2; V := V1; if IsTetaSmall then alfa := (m*g-Cy0*q*S)/(P+Cya*q*S) else begin aa := (a1*q+a2*P)*q+sqr(P); bb := (b1*q+b2*P)*q; cc := (c1*q+c2*P)*q+sqr(P)+c3*sqr(g); Quadr(aa,bb,cc,x1,x2,Result); alfa := x1; end; sinf := (P-(Cx0+A*sqr(Cy0+Cya*alfa))*q*S)/(m*g); if sinf < 0 then Func2 := Max else Func2 := (H2-H1)/(V*sinf); end; { - Func2 - } function TNavApp.Func3; var aa,bb,cc,l : RealType; sinf : RealType; x1,x2 : RealType; Result : Byte; begin H := (H1+H2)/2; V := (V1+V2)/2; l := sqr(g*k/(g*k+V)); if IsTetaSmall then alfa := (m*g-Cy0*q*S)/(P+Cya*q*S) else begin aa := ((a11*l+a12)*q+(a21*l+a22)*P)*q+sqr(P); bb := ((b11*l+b12)*q+(b21*l+b22)*P)*q; cc := ((c11*l+c12)*q+c2*l*P)*q+sqr(P)+c3*sqr(g); Quadr(aa,bb,cc,x1,x2,Result); alfa := x1; end; sinf := (P-(Cx0+A*sqr(Cy0+Cya*alfa))*q*S)/(m*g); if sinf < 0 then Func3 := Max else Func3 := (H2-H1)/(V*sinf); end; { - Func3 - } var NavApp : TNavApp; { Основная программа - } begin NavApp.Init; NavApp.Run; NavApp.Done; end.