unit DSW; interface uses gltype, mathobj; function TElectro_DSW(at,adt:RealType;var time,dtime:RealType; var AU,AY:TPtrExt;var AX,ADX:array of RealType; var CU,CY : TIntArray;var Prop:TPtrArray;var Vars:Pointer; Action:Integer):Integer;export; //-------------------------------------------------------------// implementation //-------------------------------------------------------------// type PElectro_DSWRec = ^TElectro_DSWRec; TElectro_DSWRec = record Rds,Rqs: ^realtype; Lds,Lqs: ^realtype; l,J : ^realtype; Rdr,Rqr: ^realtype; Ldr,Lqr: ^realtype; Ldm,Lqm: ^realtype; p,phi : ^integer; q0 : ^realtype; pq0 : ^realtype; P10 : ^realtype; P20 : ^realtype; P30 : ^realtype; P40 : ^realtype; end; PElectro_DSWVars = ^TElectro_DSWVars; TElectro_DSWVars = record Dd,Dq, K11,K12,K13, K21,K22,K23, K31,K32, K41,K42, C11,C12,C13, C21,C22, K10, K : realtype; end; function TElectro_DSW;export; var i : Integer; qm,Vd,Vq : realtype; // угол поворота магнитного поля и напряжения во вращающейся СК begin Result := 0; case Action of // Выделяем память под переменные блока f_Create : Vars := New(PElectro_DSWVars); // Освобождаем память переменных блока f_Free : Dispose(Vars); // Указываем количесво переменных состояния f_GetDeriCount : Result := 6; //FIXME : нужен ли этот флаг?? : // f_GetStateCount : Result := 0; f_GetInit : Result := 1; f_GetCount : begin for i:=0 to (CY.Count-1) do CY.arr^[i]:=1; // размер четырёх выходов строго определён for i:=0 to (CU.Count-1) do CU.arr^[i]:=1; // и трёх входов тоже ( 1 ) end; f_InitState : with PElectro_DSWRec(Prop.arr)^ do begin // Подсчёт констант (через вновь введённые свойства блока): PElectro_DSWVars(Vars)^.Dd := Lds^*Ldr^-Ldm^*Ldm^; PElectro_DSWVars(Vars)^.Dq := Lqs^*Lqr^-Lqm^*Lqm^; PElectro_DSWVars(Vars)^.K11:= Rds^*Ldr^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K12:= Rds^*Ldm^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K13:= Rds^*Ldr^*l^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K21:= Rdr^*Lds^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K22:= Rdr^*Ldm^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K23:= Rdr^*Ldm^*l^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.K31:= Rqs^*Lqr^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.K32:= Rqs^*Lqm^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.K41:= Rqr^*Lqs^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.K42:= Rqr^*Lqm^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.C11:= Ldr^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.C12:= Ldm^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.C13:= Ldr^*l^/PElectro_DSWVars(Vars)^.Dd; PElectro_DSWVars(Vars)^.C21:= Lqr^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.C22:= Lqm^/PElectro_DSWVars(Vars)^.Dq; PElectro_DSWVars(Vars)^.K10:= 1/J^; PElectro_DSWVars(Vars)^.K := 0.5*phi^*p^; //инициальзация переменных состояния из вновь введённых начальных условий: AX[0]:=P10^; AX[1]:=P20^; AX[2]:=P30^; AX[3]:=P40^; AX[4]:=pq0^; AX[5]:=q0^; //Инициализация выходов в начальный момент времени: AY.Ptr(0).arr^[0] := PElectro_DSWVars(Vars)^.C11*AX[0] - PElectro_DSWVars(Vars)^.C12*AX[2] - PElectro_DSWVars(Vars)^.C13; //id AY.Ptr(1).arr^[0] := PElectro_DSWVars(Vars)^.C21*AX[1] - PElectro_DSWVars(Vars)^.C22*AX[3]; //iq AY.Ptr(2).arr^[0] := AX[4]; //pq AY.Ptr(3).arr^[0] := AX[5]; //q AY.Ptr(4).arr^[0] := PElectro_DSWVars(Vars)^.K* (AX[0]*AY.Ptr(1).arr^[0] - AX[1]*AY.Ptr(0).arr^[0]);//Te = ... end; f_UpdateJacoby, f_UpDateOuts, f_RestoreOuts, f_GoodStep : with PElectro_DSWRec(Prop.arr)^ do begin //Расчёт выходов (на каждом шаге): AY.Ptr(0).arr^[0] := PElectro_DSWVars(Vars)^.C11*AX[0] - PElectro_DSWVars(Vars)^.C12*AX[2] - PElectro_DSWVars(Vars)^.C13; //id AY.Ptr(1).arr^[0] := PElectro_DSWVars(Vars)^.C21*AX[1] - PElectro_DSWVars(Vars)^.C22*AX[3]; //iq AY.Ptr(2).arr^[0] := AX[4]; //pq AY.Ptr(3).arr^[0] := AX[5]; //q AY.Ptr(4).arr^[0] := PElectro_DSWVars(Vars)^.K* (AX[0]*AY.Ptr(1).arr^[0] - AX[1]*AY.Ptr(0).arr^[0]); //Te = ... end; //расчёт приращений: f_GetDeri : with PElectro_DSWRec(Prop.arr)^ do begin qm := p^*AX[5]; //угол поворота магнитного поля //пересчитываем напряжения во вращающихся обмотках: Vd := AU.Ptr(0).arr^[0]*sin(qm)-AU.Ptr(1).arr^[0]*cos(qm); Vq := AU.Ptr(0).arr^[0]*cos(qm)+AU.Ptr(1).arr^[0]*sin(qm); ADX[0] := Vd -PElectro_DSWVars(Vars)^.K11*AX[0] +PElectro_DSWVars(Vars)^.K12*AX[2] +PElectro_DSWVars(Vars)^.K13 +p^*AX[1]*AX[4]; ADX[1] := Vq -PElectro_DSWVars(Vars)^.K31*AX[1] +PElectro_DSWVars(Vars)^.K32*AX[3] -p^*AX[0]*AX[4]; ADX[2] :=-PElectro_DSWVars(Vars)^.K21*AX[2] +PElectro_DSWVars(Vars)^.K22*AX[0] +PElectro_DSWVars(Vars)^.K23; ADX[3] :=-PElectro_DSWVars(Vars)^.K41*AX[3] +PElectro_DSWVars(Vars)^.K42*AX[1]; ADX[4] := PElectro_DSWVars(Vars)^.K10*((PElectro_DSWVars(Vars)^.K*(AX[0]*(PElectro_DSWVars(Vars)^.C21*AX[1]-PElectro_DSWVars(Vars)^.C22*AX[3])-AX[1]*(PElectro_DSWVars(Vars)^.C11*AX[0]-PElectro_DSWVars(Vars)^.C12*AX[2]-PElectro_DSWVars(Vars)^.C13)))-AU.Ptr(2).arr^[0]); ADX[5] := AX[4]; end; end; // case end; //TElectro_DSW end.