00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 char et_rot_isco_C[] = "$Header: /cvsroot/Lorene/C++/Source/Etoile/et_rot_isco.C,v 1.3 2011/01/07 18:20:08 m_bejger Exp $" ;
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060 #include <math.h>
00061
00062
00063 #include "etoile.h"
00064 #include "param.h"
00065 #include "utilitaires.h"
00066
00067 double fonct_etoile_rot_isco(double, const Param&) ;
00068
00069
00070
00071
00072
00073
00074 double Etoile_rot::r_isco(ostream* ost) const {
00075
00076 if (p_r_isco == 0x0) {
00077
00078
00079
00080
00081 int nzm1 = mp.get_mg()->get_nzone() - 1 ;
00082 Cmp dnphi = nphi().dsdr() ;
00083 dnphi.annule(nzm1) ;
00084 Cmp ddnphi = dnphi.dsdr() ;
00085
00086 Cmp tmp = nnn().dsdr() ;
00087 tmp.annule(nzm1) ;
00088 Cmp ddnnn = tmp.dsdr() ;
00089
00090 tmp = bbb().dsdr() ;
00091 tmp.annule(nzm1) ;
00092 Cmp ddbbb = tmp.dsdr() ;
00093
00094
00095
00096
00097 Cmp bdlog = bbb().dsdr() / bbb() ;
00098 Cmp ndlog = nnn().dsdr() / nnn() ;
00099 Cmp bsn = bbb() / nnn() ;
00100
00101 Cmp r(mp) ;
00102 r = mp.r ;
00103
00104 Cmp r2= r*r ;
00105
00106 bdlog.annule(nzm1) ;
00107 ndlog.annule(nzm1) ;
00108 bsn.annule(nzm1) ;
00109 r2.annule(nzm1) ;
00110
00111
00112 Cmp ucor_plus = (r2 * bsn * dnphi +
00113 sqrt ( r2 * r2 * bsn *bsn * dnphi * dnphi +
00114 4 * r2 * bdlog * ndlog + 4 * r * ndlog) ) /
00115 2 / (1 + r * bdlog ) ;
00116
00117 Cmp factor_u2 = r2 * (2 * ddbbb / bbb() - 2 * bdlog * bdlog +
00118 4 * bdlog * ndlog ) +
00119 2 * r2 * r2 * bsn * bsn * dnphi * dnphi +
00120 4 * r * ( ndlog - bdlog ) - 6 ;
00121
00122 Cmp factor_u1 = 2 * r * r2 * bsn * ( 2 * ( ndlog - bdlog ) *
00123 dnphi - ddnphi ) ;
00124
00125 Cmp factor_u0 = - r2 * ( 2 * ddnnn / nnn() - 2 * ndlog * ndlog +
00126 4 * bdlog * ndlog ) ;
00127
00128
00129 Cmp orbit = factor_u2 * ucor_plus * ucor_plus +
00130 factor_u1 * ucor_plus + factor_u0 ;
00131 orbit.std_base_scal() ;
00132
00133
00134
00135
00136 double r_ms, theta_ms, phi_ms, xi_ms,
00137 xi_min = -1, xi_max = 1;
00138 int l_ms = nzet, l ;
00139 bool find_status = false ;
00140
00141 const Valeur& vorbit = orbit.va ;
00142
00143 for(l = nzet; l <= nzm1; l++) {
00144
00145
00146
00147 theta_ms = M_PI / 2. ;
00148 phi_ms = 0. ;
00149
00150 xi_min = -1. ;
00151 xi_max = 1. ;
00152
00153 double resloc_old ;
00154 double xi_f = xi_min;
00155
00156 double resloc = vorbit.val_point(l, xi_min, theta_ms, phi_ms) ;
00157
00158 for (int iloc=0; iloc<200; iloc++) {
00159 xi_f = xi_f + 0.01 ;
00160 resloc_old = resloc ;
00161 resloc = vorbit.val_point(l, xi_f, theta_ms, phi_ms) ;
00162 if ( resloc * resloc_old < double(0) ) {
00163 xi_min = xi_f - 0.01 ;
00164 xi_max = xi_f ;
00165 l_ms = l ;
00166 find_status = true ;
00167 break ;
00168 }
00169
00170 }
00171
00172 }
00173
00174 Param par_ms ;
00175 par_ms.add_int(l_ms) ;
00176 par_ms.add_cmp(orbit) ;
00177
00178 if(find_status) {
00179
00180 double precis_ms = 1.e-13 ;
00181 int nitermax_ms = 200 ;
00182
00183 int niter ;
00184 xi_ms = zerosec(fonct_etoile_rot_isco, par_ms, xi_min, xi_max,
00185 precis_ms, nitermax_ms, niter) ;
00186
00187 if (ost != 0x0) {
00188 * ost <<
00189 " number of iterations used in zerosec to locate the ISCO : "
00190 << niter << endl ;
00191 *ost << " zero found at xi = " << xi_ms << endl ;
00192 }
00193
00194 r_ms = mp.val_r(l_ms, xi_ms, theta_ms, phi_ms) ;
00195
00196 } else {
00197
00198
00199 r_ms = ray_eq() ;
00200 xi_ms = -1 ;
00201 l_ms = nzet ;
00202
00203 }
00204
00205 p_r_isco = new double ((bbb().va).val_point(l_ms, xi_ms, theta_ms, phi_ms)
00206 * r_ms ) ;
00207
00208
00209
00210
00211 ucor_plus.std_base_scal() ;
00212 double ucor_msplus = (ucor_plus.va).val_point(l_ms, xi_ms, theta_ms,
00213 phi_ms) ;
00214 double nobrs = (bsn.va).val_point(l_ms, xi_ms, theta_ms, phi_ms) ;
00215 double nphirs = (nphi().va).val_point(l_ms, xi_ms, theta_ms, phi_ms) ;
00216
00217 p_f_isco = new double ( ( ucor_msplus / nobrs / r_ms + nphirs ) /
00218 (double(2) * M_PI) ) ;
00219
00220
00221
00222 p_lspec_isco=new double (ucor_msplus/sqrt(1.-ucor_msplus*ucor_msplus)*
00223 ((bbb().va).val_point(l_ms, xi_ms, theta_ms, phi_ms)) * r_ms );
00224
00225
00226
00227 p_espec_isco=new double (( 1./nobrs / r_ms / ucor_msplus + nphirs) *
00228 (ucor_msplus/sqrt(1.-ucor_msplus*ucor_msplus)*
00229 ((bbb().va).val_point(l_ms, xi_ms, theta_ms, phi_ms)) * r_ms ));
00230
00231
00232
00233
00234 double ucor_eqplus = (ucor_plus.va).val_point(l_ms, -1, theta_ms, phi_ms) ;
00235 double nobeq = (bsn.va).val_point(l_ms, -1, theta_ms, phi_ms) ;
00236 double nphieq = (nphi().va).val_point(l_ms, -1, theta_ms, phi_ms) ;
00237
00238 p_f_eq = new double ( ( ucor_eqplus / nobeq / ray_eq() + nphieq ) /
00239 (double(2) * M_PI) ) ;
00240
00241 }
00242
00243 return *p_r_isco ;
00244
00245 }
00246
00247
00248
00249
00250
00251 double Etoile_rot::f_isco() const {
00252
00253 if (p_f_isco == 0x0) {
00254
00255 r_isco() ;
00256
00257 assert(p_f_isco != 0x0) ;
00258 }
00259
00260 return *p_f_isco ;
00261
00262 }
00263
00264
00265
00266
00267
00268 double Etoile_rot::lspec_isco() const {
00269
00270 if (p_lspec_isco == 0x0) {
00271
00272 r_isco() ;
00273
00274 assert(p_lspec_isco != 0x0) ;
00275 }
00276
00277 return *p_lspec_isco ;
00278
00279 }
00280
00281
00282
00283
00284
00285 double Etoile_rot::espec_isco() const {
00286
00287 if (p_espec_isco == 0x0) {
00288
00289 r_isco() ;
00290
00291 assert(p_espec_isco != 0x0) ;
00292 }
00293
00294 return *p_espec_isco ;
00295
00296 }
00297
00298
00299
00300
00301
00302
00303 double Etoile_rot::f_eq() const {
00304
00305 if (p_f_eq == 0x0) {
00306
00307 r_isco() ;
00308
00309 assert(p_f_eq != 0x0) ;
00310 }
00311
00312 return *p_f_eq ;
00313
00314 }
00315
00316
00317
00318
00319
00320
00321
00322 double fonct_etoile_rot_isco(double xi, const Param& par){
00323
00324
00325 int l_ms = par.get_int() ;
00326 const Cmp& orbit = par.get_cmp() ;
00327 const Valeur& vorbit = orbit.va ;
00328
00329
00330 double theta = M_PI / 2. ;
00331 double phi = 0 ;
00332 return vorbit.val_point(l_ms, xi, theta, phi) ;
00333
00334 }
00335