Beispiel #1
0
 def cloud_shock(self, conduction_flag=False, verbose=False):
     v_shock_approx = self.r_c / self.tau_cc
     fac_ram = bowshock.ram_pressure_fac(self.mach) * params.ram
     p_ps = fac_ram * self.rho_a * self.vrel**2
     v_shock = sqrt(p_ps / self.p_c) * self.cs_c
     self.rho_c = self.rho_a * (self.vrel / self.cs_c)**2
     # self.rho_c = self.rho_c * (v_shock / self.cs_c) ** 2
     self.r_c = (self.M_c / self.rho_c / pi)**(1. / 3.
                                               )  # cylindrical geometry
     if (conduction_flag == True):
         T_ps = bowshock.rh_temperature_ratio(self.mach) * params.T_ps
         if (T_ps < 1): T_ps = 1
         T_ps = T_ps * self.T_a
         n_ps = self.n_a * bowshock.rh_density_ratio(
             self.mach) * params.n_ps
         # self.rho_c *= conduction.evap_pressure_fac(self.r_c, self.n_a, self.T_a)
     else:
         n_ps, T_ps = self.n_a, self.T_a
     self.rho_c *= conduction.evap_pressure_fac(self.r_c, n_ps, T_ps)
     print "fac =", conduction.evap_pressure_fac(self.r_c, n_ps, T_ps)
     self.n_c = self.rho_c / (pc.mh * 1.30)
     p_therm_c = self.n_c * self.T_c * pc.k
     p_therm_a = n_ps * T_ps * pc.k
     print "c_evap = ", conduction.evap_pressure_fac(self.r_c, n_ps, T_ps) * p_therm_a * \
         4. * pi * self.r_c ** 2 / conduction.mass_loss_rate(self.r_c, n_ps, T_ps) / (1.e5)
     self.r_c = (self.M_c / self.rho_c / pi)**(1. / 3.
                                               )  # cylindrical geometry
     v_ps = v_shock - self.cs_c**2 / v_shock  # post-shock velocity in rest-frame
     p_cond = conduction.evap_pressure_fac(self.r_c, n_ps, T_ps) * p_therm_a
     self.tau_evap = conduction.tau_evap(self.M_c, self.r_c, n_ps, T_ps)
     self.tau_khi = bowshock.fac_khi(self.mach) * self.tau_cc
     self.N_c = self.M_c / (1.30 * pc.mh * pi * self.r_c * self.r_c)
     self.L = self.r_c
     # self.vrel = self.vrel - v_shock
     fac_ram = bowshock.ram_pressure_fac(self.mach) * params.ram
     p_ps = fac_ram * self.rho_a * self.vrel**2
     # self.a_ram = (p_ps - p_therm_a) * pi * self.r_c ** 2 / self.M_c
     self.a_ram = (p_ps - self.T_a * self.n_a * pc.k) * pi * (
         0.1 * ac.kpc)**2 / self.M_c
     self.vrel = self.vrel - self.a_ram * self.tau_cc
     if (verbose == True):
         print ""
         print "Post Cloud Shock"
         print "--------------------------------"
         print "n_c = ", self.n_c, "[cm^-3]"
         print "R_c = ", self.r_c / ac.kpc * 1.e3, "[pc]"
         print "v_shock = ", v_shock / 1.e5, "[km/s]"
         print "v_shock_approx = ", v_shock_approx / 1.e5, "[km/s]"
         print "Pc/k = ", p_therm_c / pc.k, "[K]"
         print "Pa/k = ", p_therm_a / pc.k, "[K]"
         print "Pps/k = ", p_ps / pc.k, "[K]"
         print "Pcond/k = ", p_cond / pc.k, "[K]"
         print "sigma0 = ", conduction.sigma_cond(self.r_c, n_ps, T_ps)
         print "t_cc = ", self.tau_cc / 1.e6 / ac.yr, "[Myr]"
         print "t_khi = ", self.tau_khi / 1.e6 / ac.yr, "[Myr]"
         print "t_evap = ", self.tau_evap / 1.e6 / ac.yr, "[Myr]"
         print "N_c = ", self.N_c, "[cm^-2]"
Beispiel #2
0
 def cloud_shock(self):
     v_shock_approx = self.r_c / self.tau_cc
     T_ps = bowshock.rh_temperature_ratio(self.mach) * self.tau_s
     if (T_ps < 1): T_ps = 1
     T_ps = T_ps * self.T_a
     n_ps = self.n_a * bowshock.rh_density_ratio(self.mach) * self.eta_s
     p_ps = n_ps * T_ps * pc.k
     p_therm_c = self.n_c * self.T_c * pc.k
     p_therm_a = self.n_a * self.T_a * pc.k
     self.v_shock = sqrt(p_ps / self.p_c) * self.cs_c
     # WARNING: Ignore the pressure difference between stagnation point and the shock front
     # if(self.mach < 1.2):
     #     p_ps *= bowshock.postshock_pressure_fac(self.mach)
     self.rho_c = self.rho_c * p_ps / p_therm_a  # Isothermal shock condition
     self.r_c = (self.M_c / self.rho_c / pi)**(1. / 3.
                                               )  # cylindrical geometry
     self.n_c = self.rho_c / (pc.mh * self.mu)  # Assuming neutral
     self.r_c = (self.M_c / self.rho_c / pi)**(1. / 3.
                                               )  # cylindrical geometry
     p_cond = conduction.evap_pressure_fac(self.r_c, n_ps, T_ps) * p_therm_a
     self.tau_evap = conduction.tau_evap(self.M_c, self.r_c, n_ps,
                                         T_ps) * self.f_cond
     self.tau_khi = bowshock.fac_khi(self.mach) * self.tau_cc
     self.N_c = self.M_c / (self.mu * pc.mh * pi * self.r_c * self.r_c)
     self.L = self.r_c
     # self.vrel = self.vrel - v_shock
     # fac_ram = bowshock.ram_pressure_fac(self.mach) * params.ram
     # p_ps = fac_ram * self.rho_a * self.vrel ** 2
     self.a_ram = (p_ps - p_therm_a) * pi * (self.r_c)**2 / self.M_c
Beispiel #3
0
 def cloud_shock(self):
     self.v_shock_approx = self.r_c / self.tau_cc  # Good when conduction is not dynamically important
     T_ps = max(self.tau_s, 1.0)
     T_ps = T_ps * self.T_a
     n_ps = self.n_a * self.eta_s
     p_ps = n_ps * T_ps * pc.k
     p_therm_c = self.n_c * self.T_c * pc.k
     p_therm_a = self.n_a * self.T_a * pc.k
     self.v_shock = sqrt(p_ps / self.p_c) * self.cs_c
     self.rho_c = self.rho_c * p_ps / p_therm_a
     # ----------------------------------------------------------------
     # note 1: How do we define R_c after cloud shock?
     self.r_c = (0.75 * self.M_c / self.rho_c / pi)**(1. / 3.
                                                      )  # # SPHERICAL cloud
     if (ADJUST_RCLOUD_FOR_VAPORPRESSURE):
         p_evap = 3.59 * conduction.sigma_cond(self.r_c, n_ps, T_ps)**0.28
         self.rho_c *= p_evap
         rc_prev = self.r_c
         self.r_c *= (p_evap)**(-1. / 3.)
         print "p_evap = %5.3f, r_c(before) = %5.3f pc, r_c(now) = %5.3f pc" % (
             p_evap, rc_prev / ac.pc, self.r_c / ac.pc)
     # L_c changes according the internal structure we assume
     # ----------------------------------------------------------------
     self.n_c = self.rho_c / (pc.mh * self.mu)  # Assuming neutral
     p_evap = conduction.evap_pressure_fac(self.r_c, n_ps, T_ps) * p_therm_a
     self.tau_evap = conduction.tau_evap(self.M_c, self.r_c, n_ps,
                                         T_ps) * self.f_cond
     self.tau_khi = bowshock.fac_khi(self.mach) * self.tau_cc
     self.a_ram = p_ps * pi * (
         self.r_c)**2 / self.M_c / self.pressure_factor
     self.debug_flag = 1
Beispiel #4
0
 def cloud_shock(self):
     self.v_shock_approx = self.r_c / self.tau_cc  # Good when conduction is not dynamically important
     T_ps = max(self.tau_s, 1.0)
     T_ps = T_ps * self.T_a
     n_ps = self.n_a * self.eta_s
     p_ps = n_ps * T_ps * pc.k
     p_therm_c = self.n_c * self.T_c * pc.k
     p_therm_a = self.n_a * self.T_a * pc.k
     self.v_shock = sqrt(p_ps / self.p_c) * self.cs_c
     # WARNING: Ignore the pressure difference between stagnation point and the shock front
     # if(self.mach < 1.2):
     #     p_ps *= bowshock.postshock_pressure_fac(self.mach)
     self.rho_c = self.rho_c * p_ps / p_therm_a  # Isothermal shock condition
     if (USE_MINIMUM_EXPANSION_SPEED):
         self.v_max = self.v_shock_approx / self.cs_c - 3.0  # upper limit
         # self.v_max = self.v_shock_approx # upper limit
         self.v_max = min(self.v_max, log(self.rho_c / self.rho_c0))
     else:
         self.v_max = log(self.rho_c / self.rho_c0)
     print "v_shock_approx = %5.3f; v_shock = %5.3f; c*log(rho_c/rho_c0) = %5.3f" % (
         self.v_shock_approx / 1.e5, self.v_shock / 1.e5,
         log(self.rho_c / self.rho_c0) * self.cs_c / 1.e5)
     # self.v_max = log(self.rho_c/self.rho_c0)
     self.v_max0 = self.v_max
     # ----------------------------------------------------------------
     # note 1: How do we define R_c after cloud shock?
     self.r_c = (self.M_c / self.rho_c / pi / 2.)**(
         1. / 3.)  # cylindrical geometry
     p_evap_ratio = conduction.evap_pressure_fac(self.r_c, n_ps, T_ps)
     print " ---> P_evap initial: ", p_evap_ratio
     if (ADJUST_RHOC_WITH_PEVAP):
         if (p_evap_ratio > 1):
             self.rho_c *= p_evap_ratio
             self.r_c *= (p_evap_ratio)**(-1. / 3.)
     # L_c changes according the internal structure we assume
     # 180712: We no longer accept the case with constant density!
     self.L = 2. * self.r_c
     self.tau_sc = 2.0 * self.r_c / self.cs_c
     if (self.n_poly == 1.0):
         # self.L = self.r_c * self.v_max # isothermal, 5.0 by default, constrained from x300v1700
         self.L = self.r_c * 4.0
         self.v_max = self.v_max
     else:
         self.L = self.r_c * (self.n_poly + 1.0) / (self.n_poly - 1.0)
     # ----------------------------------------------------------------
     self.n_c = self.rho_c / (pc.mh * self.mu)  # Assuming neutral
     self.tau_evap = conduction.tau_evap(self.M_c, self.r_c, n_ps,
                                         T_ps) / self.f_cond
     self.tau_khi = bowshock.fac_khi(self.mach) * self.tau_cc
     self.N_c = self.M_c / (self.mu * pc.mh * pi * self.r_c * self.r_c)
     # self.vrel = self.vrel - v_shock
     # fac_ram = bowshock.ram_pressure_fac(self.mach) * params.ram
     # p_ps = fac_ram * self.rho_a * self.vrel ** 2
     self.a_ram = p_ps * pi * (
         self.r_c)**2 / self.M_c / self.pressure_factor
     self.debug_flag = 1
Beispiel #5
0
    def dynamical_update(self,
                         dt,
                         verbose=False,
                         conduction_flag=True,
                         compression_flag=False,
                         geometry="spherical"):
        if (conduction_flag == True):
            # TRICK
            # self.a_ram *= conduction.evap_pressure_fac(self.r_c, self.n_a, self.T_a)
            T_ps = bowshock.rh_temperature_ratio(self.mach) * params.T_ps
            if (T_ps < 1): T_ps = 1
            T_ps = T_ps * self.T_a
            n_ps = self.n_a * bowshock.rh_density_ratio(
                self.mach) * params.n_ps
        else:
            T_ps, n_ps = self.T_a, self.n_a
        self.tau_evap = conduction.tau_evap(self.M_c, self.r_c, n_ps, T_ps)
        # print self.tau_evap / ac.yr / 1.e6, n_ps, T_ps, self.r_c, self.L
        if (geometry == "cylindrical"):
            self.tau_evap = self.tau_evap / (self.L / (2.0 * self.r_c))
            # self.tau_evap = self.tau_evap
        mlr = conduction.mass_loss_rate(self.r_c, n_ps, T_ps) * 0.5
        mlr += conduction.mass_loss_rate(self.r_c, self.n_a,
                                         self.T_a) * self.L / (2.0 * self.r_c)
        self.tau_evap = self.M_c / mlr
        print mlr / (conduction.mass_loss_rate(self.r_c, n_ps, T_ps) * 0.5)
        # Calculate Acceleration
        fac_ram = bowshock.ram_pressure_fac(self.mach) * params.ram
        p_ps = fac_ram * self.rho_a * self.vrel**2
        p_therm_c = self.n_c * self.T_c * pc.k
        # p_therm_a = n_ps * T_ps * pc.k
        p_therm_a = self.n_a * self.T_a * pc.k
        self.a_ram = (p_ps - p_therm_a) * pi * self.r_c**2 / self.M_c
        self.tau_khi = bowshock.fac_khi(self.mach) * self.tau_cc
        # Update Cloud Properties
        self.time = self.time + dt
        self.r = self.r + self.vrel * dt
        self.vrel = self.vrel - self.a_ram * dt
        self.mach = self.vrel / self.cs_a
        self.M_c = self.M_c * exp(-dt / self.tau_evap)
        # self.M_c = self.M_c * exp(-dt / self.tau_khi)
        # TRICK
        # rho_eq = conduction.evap_pressure_fac(self.r_c, n_ps, T_ps) * (n_ps / self.n_a) * self.rho_a * T_ps / self.T_c
        # print rho_eq, self.rho_c, n_ps, T_ps, conduction.evap_pressure_fac(self.r_c, self.n_a, T_ps)
        # rho_eq = self.rho_a * self.T_a / self.T_c
        # print rho_eq, self.n_a, self.T_a, conduction.evap_pressure_fac(self.r_c, self.n_a, self.T_a)
        rho_eq = conduction.evap_pressure_fac(
            self.r_c, self.n_a, self.T_a) * self.rho_a * self.T_a / self.T_c
        if (compression_flag == False):
            L_eq = self.M_c / (rho_eq * self.r_c * self.r_c * pi)
            self.L = self.L + self.cs_c * dt * 3.0
            # Here using free expansion approximation: v = 2.0 * c / (gamma - 1)
            self.r_c = sqrt(self.M_c / (self.N_c * pc.mh * 1.30) / pi)
            if (self.L > L_eq):
                self.L = L_eq
        else:
            L_eq = self.M_c / (
                (self.T_a * self.rho_a / self.T_c) * self.r_c * self.r_c * pi)
            # Lower pressure (no vapor pressure), therefore longer L_eq
            self.L = self.L + self.cs_c * dt * 3.0
            if (self.L > L_eq): self.L = L_eq
            self.rho_c = self.M_c / (self.L * self.r_c * self.r_c * pi)
            # Allow cloud size to shrink
            # However, problem is it induces a positive feedback:
            # Smaller Rc leads to higher vapor pressure and higher rho_eq, the cloud will collapse!
            if (self.rho_c < rho_eq):
                self.r_c = sqrt(self.M_c / (rho_eq * self.L * pi))

        self.rho_c = self.M_c / (self.L * self.r_c * self.r_c * pi)
        self.n_c = self.rho_c / (pc.mh * 1.30)
        if (verbose == True):
            print "%5.3f(%5.3f) %6.2f %6.1f %5.3f %6.2f(%5.3f) %6.2f %5.3f %7.2f" % \
                (self.time/ac.yr/1.e6, self.time/self.tau_cc, self.r / ac.kpc, self.vrel / 1.e5, self.M_c / M_0, \
                 self.L * 1.e3 / ac.kpc, self.L / L_eq, self.r_c * 1.e3 / ac.kpc, \
                 self.n_c, self.tau_evap / ac.yr / 1.e6)