Main Page   Class Hierarchy   Data Structures   File List   Data Fields   Globals  

add_star.C

Go to the documentation of this file.
00001 
00002        //=======================================================//    _\|/_
00003       //  __  _____           ___                    ___       //      /|\ ~
00004      //  /      |      ^     |   \  |         ^     |   \     //          _\|/_
00005     //   \__    |     / \    |___/  |        / \    |___/    //            /|\ ~
00006    //       \   |    /___\   |  \   |       /___\   |   \   // _\|/_
00007   //     ___/   |   /     \  |   \  |____  /     \  |___/  //   /|\ ~
00008  //                                                       //            _\|/_
00009 //=======================================================//              /|\ ~
00010 
00022 //++ Notes:
00023 //++  Command-line arguments overrule parameters from input snapshot.
00024 //++
00025 //++  If no time unit is explicitly specified it is derived
00026 //++  from the other units.
00027 //++
00028 //++  The mass of the system can be set independently from the total
00029 //++  mass of the input N-body system (e.g. when modeling a large
00030 //++  cluster by a smaller N-body system).
00031 //++
00032 //++  Should run makemass first to establish stellar masses.
00033 //++
00034 //++ Example of usage:
00035 //++  makenode -n 10 | makemass -u 100 -l 10 | add_star -T 1
00036 //++
00037 //++ See also:  mkmass
00038 //++            mknode
00039 //++
00042 //                           spz@grape.c.u-tokyo.ac.jp
00043 
00044 #include "single_star.h"
00045 
00046 #ifndef TOOLBOX
00047 
00048 //-----------------------------------------------------------------------------
00049 //  addstar  -- for all particles, add a star part using "new star()".
00050 //-----------------------------------------------------------------------------
00051 
00052 void  addstar(node * b, real t_current, stellar_type type, bool verbose)
00053 {
00054   //    if(!((star*)b->get_starbase())->get_seba_counters()) {
00055   //      cerr << "Initialize SeBa counters" << endl;
00056   //      ((star*)b->get_starbase())->set_seba_counters(new seba_counters);
00057   //    }
00058 
00059     if (b->get_oldest_daughter() != NULL) {
00060 
00061         real m_min = VERY_LARGE_NUMBER;
00062         real m_max = -VERY_LARGE_NUMBER;
00063         real m_av = 0;
00064         int  n_star = 0;
00065 
00066         for_all_daughters(node, b, bi) {
00067             addstar(bi, t_current, type, verbose);
00068 
00069             if (verbose) {
00070                 real m = bi->get_starbase()
00071                            ->conv_m_dyn_to_star(bi->get_mass());
00072                 m_min = min(m_min, m);
00073                 m_max = max(m_max, m);
00074                 m_av += m;
00075                 n_star++;               
00076             }
00077         }
00078 
00079         if (verbose) {
00080             if (n_star > 0) m_av /= n_star;
00081             //  PRC(n_star); PRC(m_min); PRC(m_max); PRL(m_av);
00082         }
00083 
00084     } else {
00085 
00086 //      cerr << "addstar: ";
00087 //      PRL(b->get_starbase()->get_element_type());
00088 
00089         // NAS is the default return value of get_element_type, in
00090         // cases where only a starbase (but no star) exists.
00091 
00092         if (b->get_starbase()->get_element_type() != NAS) return;
00093         
00094         int id = b->get_index();
00095         real t_cur=0, t_rel=0, m_rel=1, m_env=0, m_core=0.01;
00096         real T_eff, L_eff;
00097         real p_rot=0, b_fld=0;
00098         real m_tot;
00099 
00100         // Create a (single) star part, using the unformation obtained from
00101         // the star story read in by get_node(), or created from scratch.
00102 
00103         stellar_type local_type = NAS;
00104         starbase * old_starbase = b->get_starbase();
00105         story * s = old_starbase->get_star_story();
00106 
00107         real mco_core = 0;
00108         extract_story_chapter(local_type, t_cur, t_rel,
00109                               m_rel, m_env, m_core, mco_core, T_eff, L_eff,
00110                               p_rot, b_fld, *s);
00111 
00112         m_tot = m_env+m_core;
00113         old_starbase->set_star_story(NULL);
00114         delete s;
00115 
00116         if (local_type != NAS) {        // Is the star properly defined?
00117 
00118             // Use the data extracted from the star story.  Note that the
00119             // input values of the type and t_rel arguments are IGNORED.
00120 
00121           //cerr << "addstar: " << type_string(local_type)
00122           //   << " t_rel = " << t_rel << " t_cur = " << t_cur << endl;
00123         
00124             type = local_type;
00125             single_star* new_star = new_single_star(type, id, t_cur,
00126                                                     t_rel,
00127                                                     m_rel, m_tot, m_core,
00128                                                     mco_core,
00129                                                     p_rot, b_fld, b);
00130 
00131             //new_star->set_current_time(t_current); // added (SPZ:2/1998)
00132             //new_star->dump(cerr);
00133         
00134         } else {                // No star story present, or at least no
00135                                 // proper definition for a single star.
00136 
00137             // Create a default star of the specified type.
00138 
00139             real t_cur=0, t_rel = 0, m_rel = 1, m_core = 0.01;
00140             real p_rot=0, b_fld=0;
00141             real m_tot;
00142             t_cur = t_current;
00143             //cerr << "addstar2: " << type_string(type) << " t_rel = " << t_rel
00144             // << " t_cur = " << t_cur << endl;
00145 
00146             starbase * old_starbase = b->get_starbase();
00147             id = b->get_index();
00148             m_rel = m_tot = b->get_starbase()
00149                              ->conv_m_dyn_to_star(b->get_mass());
00150 
00151             stellar_type local_type = type;
00152 
00153             // Treat by dynamics pre-requested black holes
00154             if(getiq(b->get_log_story(), "black_hole")==1) {
00155               local_type = Black_Hole;
00156               m_core = m_tot;
00157               mco_core = m_tot;
00158             }
00159             else if(m_tot<cnsts.parameters(minimum_main_sequence)) {
00160               local_type = Brown_Dwarf;
00161               m_core = 0.01*m_tot;
00162               mco_core = 0;
00163             }
00164         
00165             single_star* new_star = new_single_star(local_type, id,
00166                                                     t_cur, t_rel,
00167                                                     m_rel, m_tot, m_core,
00168                                                     mco_core,
00169                                                     p_rot, b_fld, b);
00170 
00171         }
00172 
00173         // Should not be needed since new_single_star does the job.
00174         // (SPZ:25 Nov 1998)
00175         // delete old_starbase;
00176     }
00177 }
00178 
00179 #else
00180 
00181 main(int argc, char ** argv)
00182 {
00183     int  c;
00184     bool  t_flag = FALSE;
00185     bool  M_flag = FALSE;
00186     bool  R_flag = FALSE;
00187     bool  T_flag = FALSE;
00188     bool  Q_flag = FALSE;
00189     bool  s_flag = FALSE;
00190     bool  c_flag = FALSE;
00191     real  m_tot = -1;
00192     real  r_vir = -1;           // NB code length unit; may or may not
00193                                 // actually be the virial radius
00194     real  t_vir = -1;
00195     real  t_rel = 0;
00196     real  q_vir = 0.5;
00197     real  T_start = 0;
00198     stellar_type type = Main_Sequence;
00199     char * star_type_string;
00200 
00201     char  *comment;
00202     extern char *poptarg;
00203     int  pgetopt(int, char **, char *);
00204     char * param_string = "M:R:Q:T:t:s:c:";
00205 
00206     check_help();
00207 
00208     while ((c = pgetopt(argc, argv, param_string)) != -1)
00209         switch(c)
00210             {
00211             case 'M': M_flag = true;
00212                       m_tot = atof(poptarg);
00213                       break;
00214             case 'R': R_flag = TRUE;
00215                       r_vir = atof(poptarg);
00216                       break;
00217             case 'Q': Q_flag = TRUE;
00218                       q_vir = atof(poptarg);
00219                       break;
00220             case 'T': T_flag = TRUE;
00221                       t_vir = atof(poptarg);
00222                       break;
00223             case 't': T_flag = TRUE;
00224                       t_rel = atof(poptarg);
00225                       break;
00226             case 's': s_flag = true;
00227                       star_type_string = poptarg;
00228                       type = extract_stellar_type_string(star_type_string);
00229 //            case 's': s_flag = TRUE;
00230 //                      type = (stellar_type)atoi(poptarg);
00231 //                      break;
00232             case 'c': c_flag = TRUE;
00233                       comment = poptarg;
00234                       break;
00235             case '?': params_to_usage(cerr, argv[0], param_string);
00236                       get_help();
00237                       exit(1);
00238             }
00239 
00240     node *b;
00241     b = get_node(cin);
00242 
00243     if (c_flag == TRUE)
00244       b->log_comment(comment);
00245 
00246     b->log_history(argc, argv);
00247 
00248     // See if any scaling parameters are specified in the input snapshot.
00249 
00250     real new_r_vir=-1, new_t_vir=-1, new_m_tot=-1;
00251 
00252     // System mass in solar units:
00253     real old_m_tot = b->get_starbase()->conv_m_dyn_to_star(1);
00254 
00255 #define Rsun_pc 2.255e-8        // R_sun/1 parsec = 6.960e+10/3.086e+18;
00256 
00257     // Code length unit in parsecs:
00258     real old_r_vir = b->get_starbase()->conv_r_dyn_to_star(1) * Rsun_pc;
00259 
00260     // Code time unit in Myr:
00261     real old_t_vir = b->get_starbase()->conv_t_dyn_to_star(1);
00262 
00263     // Set new parameters from old ones or command line.
00264 
00265     if (old_m_tot > 0 && !M_flag)
00266         new_m_tot = old_m_tot;
00267     else if (M_flag)
00268         new_m_tot = m_tot;
00269     else
00270         err_exit("addstar: No mass scaling available.");
00271 
00272     if (old_r_vir > 0 && !R_flag)
00273         new_r_vir = old_r_vir;
00274     else
00275         new_r_vir = r_vir;
00276 
00277     if (old_t_vir > 0 && !(T_flag || Q_flag))
00278         new_t_vir = old_t_vir;
00279     else
00280         new_t_vir = t_vir;
00281 
00282     // Try to derive quantities not yet known.
00283 
00284     bool check_consistent = true;
00285 
00286     if (new_t_vir <= 0) {
00287         if (new_m_tot > 0 && new_r_vir > 0) {
00288 
00289             // If no time unit is explicitly specified, derive it from
00290             // the other units.
00291 
00292             // Standard (N-body / Heggie & Mathieu) time unit, in Myr:
00293 
00294             new_t_vir = 21.0 * sqrt(q_vir/new_m_tot) * pow(new_r_vir, 1.5);
00295             check_consistent = false;
00296         }
00297         else
00298             err_exit("addstar: Unable to set time scaling");
00299     }
00300 
00301     if (new_r_vir <= 0) {
00302         if (new_m_tot > 0 && new_t_vir > 0) {
00303 
00304             // If no length unit is explicitly specified, derive it from
00305             // the other units.
00306 
00307             new_r_vir = pow(new_t_vir / (21.0 * sqrt(q_vir/new_m_tot)), 2.0/3);
00308             check_consistent = false;
00309         }
00310         else
00311             err_exit("addstar: Unable to set radius scaling");
00312     }
00313 
00314     if (check_consistent) {
00315 
00316         // Check that the various units are consistent.
00317 
00318         real tv = 21.0 * sqrt(q_vir*pow(new_r_vir, 3)/new_m_tot);
00319         if (abs(1-new_t_vir/tv) > 1.e-4) {
00320             cerr << "Warning: inconsistent units: ";
00321             PRC(new_t_vir);
00322             PRL(tv);
00323         }
00324     }
00325 
00326     // Finally, set the scalings and create star parts.
00327 
00328     if (old_m_tot > 0 && !M_flag) {
00329 
00330         // Existing dynamical masses are to be interpreted as
00331         // solar units.  Set scaling accordingly before setting
00332         // up star parts.
00333 
00334         b->get_starbase()->set_stellar_evolution_scaling(1,1,1);
00335         addstar(b, T_start, type, true);
00336 //      addstar(b, T_start, Main_Sequence, true);
00337 
00338         // New scaling assumes that total dynamical mass will be
00339         // rescaled to 1.
00340 
00341         b->get_starbase()->set_stellar_evolution_scaling(new_m_tot,
00342                                                          new_r_vir,
00343                                                          new_t_vir);
00344     }
00345     else {
00346 
00347         // New scaling assumes that total dynamical mass will be
00348         // rescaled to 1.
00349 
00350         b->get_starbase()->set_stellar_evolution_scaling(new_m_tot,
00351                                                          new_r_vir,
00352                                                          new_t_vir);
00353 //      addstar(b, T_start, Main_Sequence, false);
00354         addstar(b, T_start, type, false);
00355     }
00356 
00357 #if 0
00358     real m_sum = 0;
00359     for_all_daughters(node, b, bi) {
00360       m_sum += bi->get_mass();
00361     }
00362     b->set_mass(m_sum);
00363 
00364     real old_mtot = b->get_starbase()->conv_m_dyn_to_star(1);
00365     if(old_mtot!=m_sum) {
00366       real old_r_vir= b->get_starbase()->conv_r_star_to_dyn(1);
00367       real old_t_vir= b->get_starbase()->conv_t_star_to_dyn(1);
00368       b->get_starbase()->set_stellar_evolution_scaling(m_sum,
00369                                                        old_r_vir,
00370                                                        old_t_vir);
00371     }
00372 #endif
00373 
00374     put_node(cout, *b); 
00375     delete b;
00376 }
00377 
00378 #endif
00379 
00380 /* endof: addstar.c */

Generated at Sun Feb 24 09:56:54 2002 for STARLAB by doxygen1.2.6 written by Dimitri van Heesch, © 1997-2001