Source code for atomicdataMB.photolossrates

"""``photolossrates`` - Determine photoionization and photodissociation rates"""
import os, os.path
import glob
import pandas as pd
import astropy.units as u
from .database_connect import database_connect


[docs]def make_photo_table(): """ Creates and populates photorates database table. Creates a database table called photorates. Fields in the table: filename Filename in project tree containing the data; used only for populating the database reference Source of the photoionization or photodissociation rate species Atomic or molecular species reaction Photoionization or photodissociation reaction If multiple reaction rates are found for a reaction, user is prompted to choose the best one. Most of the reactions are in: Huebner & Mukherjee (2015), Astrophys. Space Sci., 195, 1-294. **Parameters** None **Returns** No output """ con = database_connect() # drop the old table if necessary cur = con.cursor() cur.execute('select table_name from information_schema.tables') tables = [r[0] for r in cur.fetchall()] if 'photorates' in tables: cur.execute('''DROP TABLE photorates''') else: pass # Make the photorates table cur.execute('''CREATE TABLE photorates ( filename text, reference text, species text, reaction text, kappa float, bestvalue boolean)''') photodatafiles = glob.glob(os.path.join(os.path.dirname(__file__), 'data', 'Loss', 'Photo', '*.dat')) for f in photodatafiles: print(f' {f}') ref = '' for line in open(f): if 'reference' in line.lower(): ref = line.split('//')[0].strip() # elif 'datatype' in line.lower(): # dtype = line.split('//')[0].strip() # elif 'reactype' in line.lower(): # rtype = line.split('//')[0].strip() # elif 'ratecoefunits' in line.lower(): # un = line.split('//')[0].strip() elif len(line.split(':')) == 4: parts = line.split(':') sp = parts[0].strip() reac = parts[1].strip() kappa = parts[2].strip() cur.execute('''INSERT INTO photorates values( %s, %s, %s, %s, %s, %s)''', (f, ref, sp, reac, kappa, False)) # Look for duplicates cur.execute('SELECT DISTINCT reaction from photorates') temp = cur.fetchall() rlist = [t[0] for t in temp] for r in rlist: print(r) cur.execute('SELECT reference from photorates where reaction=%s', (r, )) if cur.rowcount > 1: temp = cur.fetchall() refs = [a[0] for a in temp] print('Reaction = {}'.format(r)) for i, a in enumerate(refs): print('({}) {}'.format(i, a)) q = 0 cur.execute('''UPDATE photorates SET bestvalue=True WHERE reaction=%s and reference=%s''', (r, refs[q])) else: cur.execute('''UPDATE photorates SET bestvalue=True WHERE reaction=%s''', (r, )) con.close()
[docs]class PhotoRate: r"""Determine photoreactions and photorates for a species. **Parameters** species Species to compute rates for. aplanet Distance from the Sun. Default is 1 AU. Given as either a numeric type or an astropy quantity with length units. **Class Attributes** species Species aplanet Distance from the Sun; astropy quantity with units AU rate Reaction rate; astropy quantity with units s^{-1}. Rate is the sum of all possible reactions for the species. reactions Pandas dataframe with columns for reaction and rate (in s^{-1}) for each reaction for the species. This can be used to determine the products produced by photolysis and photoionization. **Example** :: >>> from atomicdataMB import PhotoRate >>> kappa = PhotoRate('Na', 0.33) >>> print(kappa) Species = Na Distance = 0.33 AU Rate = 6.666666666666666e-05 1 / s >>> print(kappa.rate) 6.666666666666666e-05 1 / s >>> print(kappa.reactions) reaction kappa 0 Na, photon -> Na+, e 6.666666666666666e-05 >>> kappa = PhotoRate('H_2O') >>> print(kappa) Species = H_2O Distance = 1.0 AU Rate = 1.2056349999999999e-05 1 / s >>> print(kappa.reactions) reaction kappa 0 H_2O, photon -> H_2, O 5.97e-07 1 H_2O, photon -> OH, H 1.03e-05 2 H_2O, photon -> H, H, O 7.54e-07 3 H_2O, photon -> H, OH+, e 5.54e-08 4 H_2O, photon -> OH, H+, e 1.31e-08 5 H_2O, photon -> H_2O+, e 3.31e-07 6 H_2O, photon -> H_2, O+, e 5.85e-09 """ def __init__(self, species, aplanet_=1.*u.AU): with database_connect() as con: prates = pd.read_sql( f'''SELECT reaction, kappa FROM photorates WHERE species='{species}' and bestvalue=True''', con) try: aplanet_.value aplanet = aplanet_ except: aplanet = aplanet_*u.AU self.species = species self.aplanet = aplanet a0 = 1*u.AU # Photo rate adjusted to proper heliocentric distance if len(prates) == 0: print('No photoreactions found') self.reactions = None self.rate = 1e-30/u.s else: prates['kappa'] = prates['kappa'].apply( lambda k: k * (a0/aplanet)**2) self.reactions = prates self.rate = prates['kappa'].sum()/u.s def __str__(self): output = (f'Species = {self.species}\n' f'Distance = {self.aplanet}\n' f'Rate = {self.rate}') return output