00001
00002
00003
00004
00005 #include "super_giant.h"
00006 #include "horizontal_branch.h"
00007
00008
00009
00010
00011 super_giant::super_giant(horizontal_branch & h) : single_star(h) {
00012
00013 delete &h;
00014
00015
00016 last_update_age = next_update_age;
00017
00018 adjust_next_update_age();
00019
00020
00021 COcore_mass = initial_CO_core_mass(core_mass);
00022
00023 second_dredge_up_time = last_update_age
00024 + (next_update_age-last_update_age)
00025 * min(1., relative_mass
00026 / cnsts.parameters(super_giant2neutron_star));
00027
00028
00029 instantaneous_element(); update();
00030
00031 post_constructor();
00032 }
00033
00034 #if 0
00035 void super_giant::adjust_initial_star() {
00036
00037 if(relative_age<=0) {
00038 real t_ms = main_sequence_time();
00039 real t_giant = t_ms + hertzsprung_gap_time(t_ms)
00040 + base_giant_branch_time(t_ms);
00041 real t_he = helium_giant_time(t_ms);
00042 relative_age = max(t_giant + t_he, relative_age);
00043 }
00044 }
00045 #endif
00046
00047 void super_giant::instantaneous_element() {
00048
00049 real l_g = giant_luminosity();
00050 real t_ms = main_sequence_time();
00051 real t_gs = 0.15*t_ms;
00052 real t_b = base_giant_time(t_ms);
00053
00054 if (next_update_age + t_b - relative_age<=0)
00055 luminosity = l_g*pow(t_gs/t_b, 1.17);
00056 else
00057 luminosity = l_g*pow(t_gs/(next_update_age
00058 + t_b - relative_age), 1.17);
00059
00060 luminosity = min(luminosity, maximum_luminosity());
00061
00062
00063
00064
00065
00066 radius = (0.25*pow(luminosity, 0.4)
00067 + 0.8*pow(luminosity, 0.67))/pow(relative_mass, 0.27);
00068
00069 if(second_dredge_up_time<=0)
00070 second_dredge_up_time = last_update_age
00071 + (next_update_age-last_update_age)
00072 * min(1., relative_mass
00073 / cnsts.parameters(super_giant2neutron_star));
00074
00075 }
00076
00077
00078
00079 void super_giant::evolve_element(const real end_time) {
00080
00081 real dt = end_time - current_time;
00082 current_time = end_time;
00083 relative_age += dt;
00084
00085 if (relative_age<=next_update_age) {
00086 real l_g = giant_luminosity();
00087 real t_ms = main_sequence_time();
00088 real t_gs = 0.15*t_ms;
00089 real t_b = base_giant_time(t_ms);
00090
00091 real tau = t_gs
00092 / (next_update_age + t_b - relative_age);
00093 real tau_prev = t_gs
00094 / (next_update_age + t_b - (relative_age-dt));
00095
00096 luminosity = l_g*pow(tau, 1.17);
00097 luminosity = min(luminosity, maximum_luminosity());
00098
00099 radius = (0.25*pow(luminosity, 0.4)
00100 + 0.8*pow(luminosity, 0.67))/pow(relative_mass, 0.27);
00101
00102 real m_tot = get_total_mass();
00103
00104 real new_mcore;
00105 if(relative_mass >= cnsts.parameters(super_giant2neutron_star) ||
00106 core_mass >= cnsts.parameters(helium2neutron_star)) {
00107
00108 new_mcore = core_mass;
00109
00110
00111 real dmdt = (core_mass - COcore_mass)
00112 / (second_dredge_up_time-(relative_age-dt));
00113 COcore_mass += dmdt * dt;
00114
00115 }
00116 else {
00117 if(relative_age <= second_dredge_up_time) {
00118
00119 new_mcore = core_mass;
00120
00121
00122 real dmdt = (core_mass - COcore_mass)
00123 / (second_dredge_up_time-(relative_age-dt));
00124 COcore_mass += dmdt * dt;
00125
00126
00127 }
00128 else {
00129 if (luminosity < 15725.) {
00130 new_mcore = sqrt(luminosity/47488. + 0.1804)+0.015;
00131 }
00132 else {
00133
00134 new_mcore = luminosity/(46818*pow(relative_mass, 0.25)) + 0.46;
00135 }
00136 }
00137 }
00138
00139
00140
00141
00142 core_mass = min(m_tot, new_mcore);
00143 envelope_mass = m_tot - core_mass;
00144
00145 #if 0 // (SPZ+GN: 27 Jul 2000)
00146
00147 if (relative_mass > cnsts.parameters(super_giant2neutron_star)) {
00148 real X = cnsts.parameters(hydrogen_fraction);
00149 new_mcore = core_mass
00150 + l_g*6*t_gs*(pow(tau,1./6.)-pow(tau_prev,1./6.))
00151 / (X*cnsts.parameters(energy_to_mass_in_internal_units));
00152 }
00153 else {
00154 if (luminosity < 15725.) {
00155 new_mcore = sqrt(luminosity/47488. + 0.1804)+0.015;
00156 }
00157 else {
00158
00159 new_mcore = luminosity/(46818*pow(relative_mass, 0.25)) + 0.46;
00160 }
00161 }
00162
00163 new_mcore = max(new_mcore, core_mass);
00164
00165 core_mass = min(m_tot-cnsts.safety(minimum_mass_step), new_mcore);
00166 envelope_mass = m_tot - core_mass;
00167 #endif
00168
00169 }
00170 else {
00171 create_remnant();
00172 return;
00173 }
00174
00175 update();
00176 stellar_wind(dt);
00177 }
00178
00179 real super_giant::initial_CO_core_mass(const real initial_mass) {
00180
00181
00182
00183
00184
00185
00186
00187
00188 real final_coremass_fraction;
00189 if(initial_mass <= 0.8)
00190 final_coremass_fraction = 1;
00191 else if(initial_mass >= cnsts.parameters(helium2neutron_star))
00192 final_coremass_fraction = 0.65;
00193 else
00194 final_coremass_fraction = 1 - 0.32 * (initial_mass - 0.8);
00195
00196 return cnsts.parameters(helium_star_lifetime_fraction)
00197 * final_coremass_fraction*initial_mass;
00198 }
00199
00200 #if 0
00201 void super_giant::evolve_without_wind(const real end_time) {
00202
00203 real dt = end_time - current_time;
00204 current_time = end_time;
00205 relative_age += dt;
00206
00207 if (relative_age<=next_update_age) {
00208 real l_g = giant_luminosity();
00209 real t_ms = main_sequence_time();
00210 real t_gs = 0.15*t_ms;
00211 real t_b = base_giant_time(t_ms);
00212
00213 luminosity = l_g*pow(t_gs/(next_update_age
00214 + t_b - relative_age), 1.17);
00215 real l_max = maximum_luminosity();
00216 if(luminosity>l_max) luminosity = l_max;
00217
00218 radius = (0.25*pow(luminosity, 0.4)
00219 + 0.8*pow(luminosity, 0.67))/pow(relative_mass, 0.27);
00220 }
00221 else {
00222 create_remnant();
00223 return;
00224 }
00225
00226 update();
00227 }
00228 #endif
00229
00230 #if 0
00231
00232 void super_giant::stellar_wind(const real dt) {
00233
00234 real kappa = wind_constant;
00235 real wind_mass = 1.e6*dt*pow(kappa, 1.43)/pow(10., 13.6);
00236
00237
00238 if (wind_mass>envelope_mass)
00239 wind_mass = 0.9*envelope_mass;
00240
00241 if (is_binary_component())
00242 get_binary()->adjust_binary_after_wind_loss(this,
00243 wind_mass, dt);
00244 else
00245 reduce_mass(wind_mass);
00246 }
00247 #endif
00248
00249 #if 0
00250
00251
00252
00253
00254
00255
00256 real super_giant::helium_core_mass() {
00257
00258
00259 real m_core = (log10(luminosity) - 1.55)/3.56;
00260
00261 real m1_core = 0.073*(1 + cnsts.parameters(core_overshoot))
00262 * pow(relative_mass, 1.42);
00263
00264 real m2_core = 0.058*(1 + cnsts.parameters(core_overshoot))
00265 * pow(relative_mass, 1.57);
00266
00267 m_core = max(max(m_core, m1_core), m2_core);
00268
00269
00270
00271
00272
00273
00274
00275 if (m_core>=cnsts.parameters(helium2neutron_star) &&
00276 m_core<cnsts.parameters(minimum_helium_star))
00277 m_core = m_core<cnsts.parameters(minimum_helium_star);
00278
00279 m_core = min(m_core, get_total_mass());
00280
00281 return max(m_core, core_mass);
00282 }
00283 #endif
00284
00285 void super_giant::create_remnant() {
00286
00287 if (is_binary_component())
00288 get_binary()->dump("binev.data", false);
00289 else
00290 dump("binev.data", false);
00291
00292 real COcore_mass = 0.65 * core_mass;
00293 stellar_type type;
00294 if (relative_mass >= cnsts.parameters(maximum_main_sequence) &&
00295 relative_mass < 300)
00296 type = Disintegrated;
00297 else if (COcore_mass >= cnsts.parameters(COcore2black_hole))
00298 type = Black_Hole;
00299 else if(core_mass >= cnsts.parameters(Chandrasekar_mass))
00300 type = Neutron_Star;
00301 else
00302 type = Carbon_Dwarf;
00303
00304 switch (type) {
00305 case Black_Hole : star_transformation_story(Black_Hole);
00306 new black_hole(*this);
00307 return;
00308 case Neutron_Star : star_transformation_story(Neutron_Star);
00309 new neutron_star(*this);
00310 return;
00311 case Disintegrated : star_transformation_story(Disintegrated);
00312 new disintegrated(*this);
00313 return;
00314 case Carbon_Dwarf : star_transformation_story(Carbon_Dwarf);
00315 new white_dwarf(*this);
00316 return;
00317 default : cerr << "super_giant::create_remnant()" <<endl;
00318 cerr << "star_type not recognized." << endl;
00319 exit(-1);
00320 }
00321
00322
00323 #if 0 // (SPZ+GN: 27 Jul 2000)
00324 if (relative_mass >= cnsts.parameters(super_giant2black_hole) ||
00325 core_mass >= cnsts.parameters(helium2black_hole)) {
00326
00327 star_transformation_story(Black_Hole);
00328 new black_hole(*this);
00329 return;
00330 }
00331 else if(relative_mass >= cnsts.parameters(super_giant2neutron_star) ||
00332 core_mass >= cnsts.parameters(Chandrasekhar_mass)) {
00333
00334
00335
00336 star_transformation_story(Neutron_Star);
00337 new neutron_star(*this);
00338 return;
00339 }
00340 else if(cnsts.parameters(super_giant_disintegration)) {
00341 if (relative_mass >= 6 &&
00342 relative_mass <= cnsts.parameters(super_giant2neutron_star)) {
00343
00344 star_transformation_story(Disintegrated);
00345 new disintegrated(*this);
00346 return;
00347 }
00348 }
00349 else {
00350 if (core_mass<=cnsts.parameters(helium_dwarf_mass_limit)) {
00351 cerr << "ERROR in super_giant::create_remnant()" << endl;
00352 cerr << "Supergiants shoud not become helum dwarfs" << endl;
00353 star_transformation_story(Helium_Dwarf);
00354 }
00355 else
00356 star_transformation_story(Carbon_Dwarf);
00357
00358 new white_dwarf(*this);
00359 return;
00360 }
00361 #endif // (SPZ+GN: 27 Jul 2000)
00362
00363 }
00364
00365 star* super_giant::reduce_mass(const real mdot) {
00366
00367 if (envelope_mass<=mdot) {
00368 envelope_mass = 0;
00369
00370
00371
00372 if(relative_mass >= cnsts.parameters(super_giant2neutron_star) ||
00373 core_mass >= cnsts.parameters(helium2neutron_star)) {
00374
00375
00376
00377
00378
00379 real m_tot = core_mass;
00380 core_mass = COcore_mass;
00381 envelope_mass = m_tot - core_mass;
00382
00383 star_transformation_story(Helium_Giant);
00384 return dynamic_cast(star*, new helium_giant(*this));
00385 }
00386 else {
00387
00388
00389 if(relative_age <= second_dredge_up_time) {
00390
00391 real m_tot = core_mass;
00392 core_mass = COcore_mass;
00393 envelope_mass = m_tot - core_mass;
00394
00395 star_transformation_story(Helium_Giant);
00396 return dynamic_cast(star*, new helium_giant(*this));
00397 }
00398 else {
00399 star_transformation_story(Carbon_Dwarf);
00400 return dynamic_cast(star*, new white_dwarf(*this));
00401 }
00402 }
00403 }
00404
00405 envelope_mass -= mdot;
00406 return this;
00407 }
00408
00409 star* super_giant::subtrac_mass_from_donor(const real dt, real& mdot) {
00410
00411 real mdot_temp = relative_mass*dt/get_binary()->get_donor_timescale();
00412 mdot = mass_ratio_mdot_limit(mdot_temp);
00413
00414 if (envelope_mass<=mdot) {
00415 mdot = envelope_mass;
00416 envelope_mass = 0;
00417
00418
00419
00420 if(relative_mass >= cnsts.parameters(super_giant2neutron_star) ||
00421 core_mass >= cnsts.parameters(helium2neutron_star)) {
00422
00423 real m_tot = core_mass;
00424 core_mass = COcore_mass;
00425 envelope_mass = m_tot - core_mass;
00426
00427 star_transformation_story(Helium_Giant);
00428 return dynamic_cast(star*, new helium_giant(*this));
00429 }
00430 else {
00431
00432
00433 if(relative_age <= second_dredge_up_time) {
00434
00435 real m_tot = core_mass;
00436 core_mass = COcore_mass;
00437 envelope_mass = m_tot - core_mass;
00438
00439 star_transformation_story(Helium_Giant);
00440 return dynamic_cast(star*, new helium_giant(*this));
00441 }
00442 else {
00443 star_transformation_story(Carbon_Dwarf);
00444 return dynamic_cast(star*, new white_dwarf(*this));
00445 }
00446 }
00447
00448 }
00449
00450
00451 adjust_donor_radius(mdot);
00452
00453 envelope_mass -= mdot;
00454 return this;
00455 }
00456
00457
00458 void super_giant::adjust_accretor_age(const real mdot, const bool rejuvenate=true) {
00459
00460 real m_tot_new = get_total_mass() + mdot;
00461 real m_rel_new = max(m_tot_new, relative_mass);
00462
00463 real t_ms = main_sequence_time();
00464 real t_hg = hertzsprung_gap_time(t_ms);
00465 real t_bgb = base_giant_branch_time(t_ms);
00466 real t_he = helium_giant_time(t_ms);
00467 real t_super_old = t_ms + t_hg + t_bgb + t_he;
00468 real t_nuc = nucleair_evolution_time();
00469 real t_sg_old = t_nuc - t_super_old;
00470
00471 t_ms = main_sequence_time(m_rel_new);
00472 t_hg = hertzsprung_gap_time(m_rel_new, t_ms);
00473 t_bgb = base_giant_branch_time(m_rel_new, t_ms);
00474 t_he = helium_giant_time(m_rel_new, t_ms);
00475 real t_super_new = t_ms + t_hg + t_bgb + t_he;
00476 t_nuc = nucleair_evolution_time(m_rel_new);
00477 real t_sg_new = t_nuc - t_super_new;
00478
00479 real dtime = relative_age - t_super_old;
00480
00481
00482 last_update_age = t_super_new;
00483 relative_age = t_super_new
00484 + dtime*(t_sg_new/t_sg_old);
00485 if (rejuvenate)
00486 relative_age *= rejuvenation_fraction(mdot/m_tot_new);
00487
00488 relative_age = max(relative_age,
00489 last_update_age + cnsts.safety(minimum_timestep));
00490
00491
00492
00493
00494 }
00495
00496 void super_giant::adjust_next_update_age() {
00497
00498 next_update_age = nucleair_evolution_time();
00499 }
00500
00501 #if 0
00502
00503
00504 real super_giant::zeta_adiabatic() {
00505
00506 real x = core_mass/get_total_mass();
00507 real a = -0.220823;
00508 real b = -2.84699;
00509 real c = 32.0344;
00510 real d = -75.6863;
00511 real e = 57.8109;
00512
00513 real z = a + b*x + c*x*x + d*x*x*x + e*x*x*x*x;
00514
00515 return z;
00516 }
00517 #endif
00518
00519 real super_giant::zeta_thermal() {
00520
00521 real z = 0.;
00522
00523
00524 return z;
00525 }
00526
00527 #if 0
00528 real super_giant::stellar_radius(const real mass, const real age) {
00529
00530 real t_nuc = nucleair_evolution_time(mass);
00531
00532 real l_g = giant_luminosity();
00533 real t_ms = main_sequence_time();
00534 real t_gs = 0.15*t_ms;
00535 real t_b = base_giant_time(t_ms);
00536
00537 real l_agb = l_g*pow(t_gs/(t_nuc + t_b - age), 1.17);
00538 l_agb = min(l_agb, maximum_luminosity(mass));
00539
00540 real r_agb = (0.25*pow(l_agb, 0.4)
00541 + 0.8*pow(l_agb, 0.67))/pow(mass, 0.27);
00542
00543 return r_agb;
00544 }
00545 #endif
00546
00547
00548 real super_giant::gyration_radius_sq() {
00549
00550 return cnsts.parameters(convective_star_gyration_radius_sq);
00551 }
00552
00553 void super_giant::update_wind_constant() {
00554
00555
00556
00557
00558 if (relative_mass >= cnsts.parameters(super_giant2neutron_star)) {
00559
00560 real meader_fit_dm = 0.01*pow(relative_mass,2.);
00561 wind_constant = meader_fit_dm;
00562
00563 }
00564 else {
00565
00566
00567
00568
00569
00570
00571
00572 wind_constant = 0.8*(relative_mass - final_core_mass());
00573 }
00574
00575 wind_constant = max(wind_constant, 0.0);
00576
00577 }