00001 #include "BDSRK4Stepper.hh"
00002 #include "G4ThreeVector.hh"
00003
00005
00006
00007
00008 extern G4double BDSLocalRadiusOfCurvature;
00009
00010
00011 BDSRK4Stepper::BDSRK4Stepper(G4EquationOfMotion* EqRhs, G4int nvar) :
00012 G4MagIntegratorStepper(EqRhs,nvar)
00013 {
00014 itsEqRhs = EqRhs;
00015
00016
00017
00018 dydxr = new G4double[nvar];
00019 dydxm = new G4double[nvar];
00020 dydxt = new G4double[nvar];
00021 yt = new G4double[nvar];
00022
00023 yTemp = new G4double[nvar];
00024 yIn = new G4double[nvar];
00025 }
00026
00028
00029
00030
00031 BDSRK4Stepper::~BDSRK4Stepper()
00032 {
00033 delete[] dydxr;
00034 delete[] dydxm;
00035 delete[] dydxt;
00036 delete[] yt;
00037
00038 delete[] yTemp;
00039 delete[] yIn;
00040 }
00041
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052 void
00053 BDSRK4Stepper::AdvanceHelix( const G4double yIn[],
00054 const G4double dydx[],
00055 const G4double h,
00056 G4double yOut[])
00057 {
00058
00059
00060
00061
00062 const G4int nvar = this->GetNumberOfVariables();
00063
00064 G4int i;
00065 G4double hh = h*0.5 , h6 = h/6.0 ;
00066
00067
00068
00069
00070 yt[7] = yIn[7];
00071 yOut[7] = yIn[7];
00072
00073
00074
00075 const G4double *pIn = yIn+3;
00076 G4double itsEnergy = sqrt(pIn[0]*pIn[0]+pIn[1]*pIn[1]+pIn[2]*pIn[2]);
00077
00078 G4double BField[3];
00079 G4double Pos[4];
00080 Pos[0] = yIn[0];
00081 Pos[1] = yIn[1];
00082 Pos[2] = yIn[2];
00083 Pos[3] = 0.;
00084 itsEqRhs->GetFieldObj()->GetFieldValue(Pos,BField);
00085
00086
00087
00088
00089 G4ThreeVector BVec = G4ThreeVector(BField[0],
00090 BField[1],
00091 BField[2]);
00092 G4ThreeVector pVec = G4ThreeVector(pIn[0],
00093 pIn[1],
00094 pIn[2]);
00095
00096 G4double Bmag = (BVec.cross(pVec.unit())).mag();
00097
00098
00099 BDSLocalRadiusOfCurvature = (itsEnergy/GeV) / (0.3*Bmag/tesla)*m;
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116 for(i=0;i<nvar;i++)
00117 dydxr[i] = dydx[i];
00118
00119 RightHandSide(yIn,dydxr) ;
00120
00121
00122 for(i=0;i<nvar;i++)
00123 {
00124 yt[i] = yIn[i] + hh*dydxr[i] ;
00125 }
00126 RightHandSide(yt,dydxt) ;
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144 for(i=0;i<nvar;i++)
00145 {
00146 yt[i] = yIn[i] + hh*dydxt[i] ;
00147 }
00148 RightHandSide(yt,dydxm) ;
00149
00150 for(i=0;i<nvar;i++)
00151 {
00152 yt[i] = yIn[i] + h*dydxm[i] ;
00153 dydxm[i] += dydxt[i] ;
00154 }
00155 RightHandSide(yt,dydxt) ;
00156
00157 for(i=0;i<nvar;i++)
00158 {
00159 yOut[i] = yIn[i]+h6*(dydxr[i]+dydxt[i]+2.0*dydxm[i]);
00160 }
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172 itsDist = 0;
00173
00174 return;
00175
00176 }
00177
00178
00179 void BDSRK4Stepper::Stepper( const G4double yInput[],
00180 const G4double dydx[],
00181 const G4double hstep,
00182 G4double yOut[],
00183 G4double yErr[] )
00184 {
00185 const G4int nvar = 6 ;
00186 G4int i;
00187 const G4double *pIn = yInput+3;
00188 G4ThreeVector v0= G4ThreeVector( pIn[0], pIn[1], pIn[2]);
00189
00190
00191
00192
00193 for(i=0;i<nvar;i++) yIn[i]=yInput[i];
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211 G4double h = hstep;
00212 if(h>itsVolLength) h = itsVolLength;
00213
00214
00215 AdvanceHelix(yIn, dydx, h, yOut);
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227 for(i=0;i<nvar;i++) {
00228 yErr[i] = h*h*h*(yOut[i] - yIn[i]) ;
00229
00230 }
00231
00232
00233
00234 return;
00235 }
00236
00237 G4double BDSRK4Stepper::DistChord() const
00238 {
00239 return itsDist;
00240 }