コード例 #1
0
ファイル: mixr.py プロジェクト: graziano-giuliani/pythoncode
def mixr(t,p):
  """mx = mixr(t,p)
Computes the saturation mixing ratio given ambient temperature(s) (t) and 
pressure(s) (p).  

Inputs:
    t    = dry bulb temperature(s) (deg C or K) (vector of length N)
    p    = pressure(s) (hPa) (vector of length N)

Outputs:
    mixr = saturation mixing ratio for the given temperature and pressure

RLT, 010607
"""
  es = esat(t)
  mx = 621.97*(es/(p-es))
  return mx
コード例 #2
0
ファイル: mixr.py プロジェクト: lee-liew/pythoncode
def mixr(t, p):
    """mx = mixr(t,p)
Computes the saturation mixing ratio given ambient temperature(s) (t) and 
pressure(s) (p).  

Inputs:
    t    = dry bulb temperature(s) (deg C or K) (vector of length N)
    p    = pressure(s) (hPa) (vector of length N)

Outputs:
    mixr = saturation mixing ratio for the given temperature and pressure

RLT, 010607
"""
    es = esat(t)
    mx = 621.97 * (es / (p - es))
    return mx
コード例 #3
0
ファイル: LCLfind.py プロジェクト: cpatrizio88/thermolib
def LCLfind(Td, T, p):
    """
    LCLfind(Td, T, p)

    Finds the temperature and pressure at the lifting condensation
    level (LCL) of an air parcel.

    Parameters
    - - - - - -
    Td : float
        Dewpoint temperature (K).
    T : float
        Temperature (K).
    p : float
        Pressure (Pa)

    Returns
    - - - -
    Tlcl : float
        Temperature at the LCL (K).
    plcl : float
        Pressure at the LCL (Pa).

    Raises
    - - - -
    NameError
        If the air is saturated at a given Td and T (ie. Td >= T)
    
    Examples
    - - - - -
    >>> [Tlcl, plcl] =  LCLfind(280., 300., 8.e4)
    >>> print [Tlcl, plcl]
    [275.76250387361404, 59518.928699453245]
    >>> LCLfind(300., 280., 8.e4)
    Traceback (most recent call last):
        ...
    NameError: parcel is saturated at this pressure

    References
    - - - - - -
    Emanuel 4.6.24 p. 130 and 4.6.22 p. 129
    
    """
    c = constants()

    hit = Td >= T
    if hit is True:
        raise NameError('parcel is saturated at this pressure')

    e = esat(Td)
    ehPa = e * 0.01
    #Bolton's formula requires hPa.
    # This is is an empircal fit from for LCL temp from Bolton, 1980 MWR.
    Tlcl = (2840. / (3.5 * np.log(T) - np.log(ehPa) - 4.805)) + 55.

    r = c.eps * e / (p - e)
    #disp(sprintf('r=%0.5g',r'))
    cp = c.cpd + r * c.cpv
    logplcl = np.log(p) + cp / (c.Rd * (1 + r / c.eps)) * \
              np.log(Tlcl / T)
    plcl = np.exp(logplcl)
    #disp(sprintf('plcl=%0.5g',plcl))

    return Tlcl, plcl
コード例 #4
0
def wsat(Temp, press):
    """
    wsat(Temp, press)

    Calculates the saturation vapor mixing ratio of an air parcel.

    Parameters
    - - - - - -
    Temp : float or array_like
        Temperature in Kelvin.
    press : float or array_like
        Pressure in Pa.

    Returns
    - - - -
    theWs : float or array_like 
        Saturation water vapor mixing ratio in (kg/kg).

    Raises
    - - - -
    IOError
        If both 'Temp' and 'press' are array_like.

    Examples
    - - - - -
    >>> wsat(300, 8e4)
    0.028751159650442507
    >>> wsat([300,310], 8e4)
    [0.028751159650442507, 0.052579529573838296]
    >>> wsat(300, [8e4, 7e4])
    [0.028751159650442507, 0.033076887758679716]
    >>> wsat([300, 310], [8e4, 7e4])
    Traceback (most recent call last):
        ...
    IOError: Can't have two vector inputs.

    """
    c = constants()
    es = esat(Temp)

    # We need to test for all possible cases of (Temp,press)
    # combinations (ie. (vector,vector), (vector,scalar),
    # (scalar,vector), or (scalar,scalar).

    try:
        len(es)
    except:
        esIsVect = False
    else:
        esIsVect = True

    try:
        len(press)
    except:
        pressIsVect = False
    else:
        pressIsVect = True

    if esIsVect and pressIsVect:
        raise IOError, "Can't have two vector inputs."
    elif esIsVect:
        theWs = c.eps * es / (press - es)
        #theWs = [(c.eps * i/ (press - i)) for i in es]
        # Limit ws values so rootfinder doesn't blow up.
        #theWs = list(replaceelem(theWs,0,0.060))
    elif pressIsVect:
        theWs = c.eps * es / (press - es)
        #theWs = [(c.eps * es/ (i - es)) for i in press]
        # Limit ws values so rootfinder doesn't blow up.
        #theWs = list(replaceelem(theWs,0,0.060))
    else:  # Neither 'es' nor 'press' in a vector.
        theWs = (c.eps * es / (press - es))
        # Limit ws value so rootfinder doesn't blow up.
        if theWs > 0.060: theWs = 0.060
        elif theWs < 0: theWs = 0

    # Set minimum and maximum acceptable values for theWs.

    try:
        len(theWs)
    except:
        if theWs > 0.060: theWs = 0.060
        elif theWs < 0: theWs = 0
    else:
        theWs[theWs < 0] = 0
        theWs[theWs > 0.060] = 0.060
    #    theWs = list(replaceelem(theWs, 0, 0.060))

    return theWs
コード例 #5
0
ファイル: LCLfind.py プロジェクト: CCheng1231/A405
def LCLfind(Td, T, p):
    """
    LCLfind(Td, T, p)

    Finds the temperature and pressure at the lifting condensation
    level (LCL) of an air parcel.

    Parameters
    - - - - - -
    Td : float
        Dewpoint temperature (K).
    T : float
        Temperature (K).
    p : float
        Pressure (Pa)

    Returns
    - - - -
    Tlcl : float
        Temperature at the LCL (K).
    plcl : float
        Pressure at the LCL (Pa).

    Raises
    - - - -
    NameError
        If the air is saturated at a given Td and T (ie. Td >= T)
    
    Examples
    - - - - -
    >>> [Tlcl, plcl] =  LCLfind(280., 300., 8.e4)
    >>> print [Tlcl, plcl]
    [275.76250387361404, 59518.928699453245]
    >>> LCLfind(300., 280., 8.e4)
    Traceback (most recent call last):
        ...
    NameError: parcel is saturated at this pressure

    References
    - - - - - -
    Emanuel 4.6.24 p. 130 and 4.6.22 p. 129
    
    """
    c = constants();

    hit = Td >= T;
    if hit is True:
        raise NameError('parcel is saturated at this pressure');

    e = esat(Td);
    ehPa = e * 0.01; #Bolton's formula requires hPa.
    # This is is an empircal fit from for LCL temp from Bolton, 1980 MWR.
    Tlcl = (2840. / (3.5 * np.log(T) - np.log(ehPa) - 4.805)) + 55.;

    r = c.eps * e / (p - e);
    #disp(sprintf('r=%0.5g',r'))
    cp = c.cpd + r * c.cpv;
    logplcl = np.log(p) + cp / (c.Rd * (1 + r / c.eps)) * \
              np.log(Tlcl / T);
    plcl = np.exp(logplcl);
    #disp(sprintf('plcl=%0.5g',plcl))

    return Tlcl, plcl
コード例 #6
0
ファイル: wsat.py プロジェクト: cpatrizio88/thermolib
def wsat(Temp, press):
    """
    wsat(Temp, press)

    Calculates the saturation vapor mixing ratio of an air parcel.

    Parameters
    - - - - - -
    Temp : float or array_like
        Temperature in Kelvin.
    press : float or array_like
        Pressure in Pa.

    Returns
    - - - -
    theWs : float or array_like 
        Saturation water vapor mixing ratio in (kg/kg).

    Raises
    - - - -
    IOError
        If both 'Temp' and 'press' are array_like.

    Examples
    - - - - -
    >>> wsat(300, 8e4)
    0.028751159650442507
    >>> wsat([300,310], 8e4)
    [0.028751159650442507, 0.052579529573838296]
    >>> wsat(300, [8e4, 7e4])
    [0.028751159650442507, 0.033076887758679716]
    >>> wsat([300, 310], [8e4, 7e4])
    Traceback (most recent call last):
        ...
    IOError: Can't have two vector inputs.

    """
    c = constants();
    es = esat(Temp);

    # We need to test for all possible cases of (Temp,press)
    # combinations (ie. (vector,vector), (vector,scalar),
    # (scalar,vector), or (scalar,scalar).
    
    try:
        len(es)
    except:
        esIsVect = False
    else:
        esIsVect = True

    try:
        len(press)
    except:
        pressIsVect = False
    else:
        pressIsVect = True
    
    if esIsVect and pressIsVect:
        raise IOError, "Can't have two vector inputs."
    elif esIsVect:
        theWs = c.eps*es/(press - es)
        #theWs = [(c.eps * i/ (press - i)) for i in es]
        # Limit ws values so rootfinder doesn't blow up.       
        #theWs = list(replaceelem(theWs,0,0.060))
    elif pressIsVect:
        theWs = c.eps*es/(press - es)
        #theWs = [(c.eps * es/ (i - es)) for i in press]
        # Limit ws values so rootfinder doesn't blow up.       
        #theWs = list(replaceelem(theWs,0,0.060))
    else: # Neither 'es' nor 'press' in a vector.
        theWs = (c.eps * es/ (press - es))
        # Limit ws value so rootfinder doesn't blow up.
        if theWs > 0.060: theWs = 0.060
        elif theWs < 0: theWs = 0

    # Set minimum and maximum acceptable values for theWs.
        
    try:
        len(theWs)
    except:        
        if theWs > 0.060: theWs = 0.060
        elif theWs < 0: theWs = 0
    else:
         theWs[theWs < 0] = 0
         theWs[theWs > 0.060] = 0.060
    #    theWs = list(replaceelem(theWs, 0, 0.060))

    return theWs
コード例 #7
0
ファイル: conversion.py プロジェクト: MBlaschek/radiosonde
def humidity(x, t=288.15, p=101325, in_type='specific humidity', out_type='water vapor', nounits=False,
             method='Murphy_Koop'):
    """
    Convert Humidity data into other humidity data
    humidity:
    - partial pressure of water vapor in Pa (not hPa nor mbar)
    - specific humidity in kg/kg (not g/kg)
    - mixing ratio in kg/kg (not g/kg)
    - relative humidity in percent
    - dew point temperature in K (not degree Celsius)
    - virtual temperature in K (not degree Celsius)
    """
    in_unit = None
    out_unit = None
    ispandas = False
    inputs = ['water vapor', 'specific humidity', 'relative humidity', 'virtual temperature', 'ppmv']
    outputs = ['water vapor', 'specific humidity', 'relative humidity', 'mixing ratio', 'ppmv', 'virtual temperature',
               'dewpoint']

    if in_type not in inputs:
        print "Unkown: %s" % in_type
        print inputs

    if out_type not in outputs:
        print "Unkown: %s" % out_type
        print outputs

    # retain time information
    if isinstance(x, pd.DataFrame) | isinstance(x, pd.Series):
        # convert to numpy
        time = x.index
        if isinstance(x, pd.DataFrame):
            columns = x.columns
        x = np.ma.asarray(x)
        ispandas = True
    if isinstance(p, pd.DataFrame) | isinstance(p, pd.Series):
        p = np.ma.asarray(p)
    # Vectorize funktion or not?
    x = np.ma.asarray(x)

    c = 0.622  # Constant (Mv / Md)
    if in_type in ('partial pressure', 'partial pressure of water vapor', 'water vapor'):
        e = x
        in_unit = 'Pa'
    elif in_type == 'specific humidity':
        q = x
        e = (q * p) / (c + (1 - c) * q)
        in_unit = 'kg/kg + Pa (p)'
    elif in_type == 'mixing ratio':
        r = x
        e = (r * p) / (r + c)
        in_unit = '1 + Pa (p)'
    elif in_type == 'relative humidity':
        RH = x
        es = esat(t, method=method, info=False)
        e = (RH / 100.) * es
        in_unit = '% + K (t)'
    elif in_type == 'virtual temperature':
        Tv = x
        e = p * (1 - t / Tv) / (1 - c)
        in_unit = 'K + K (t)'
    elif in_type == 'ppmv':
        x = (x / 1e6)
        e = x * p / (1 + x)
        in_unit = 'ppmv + Pa (p)'
    else:
        print "[INPUT] Unknown Conversion"
        return

    if out_type in ('partial pressure', 'partial pressure of water vapor', 'water vapor'):
        out = e
        out_unit = 'Pa'
    elif out_type == 'specific humidity':
        Pd = p - e
        out = (e * c) / (e * c + Pd)
        out_unit = '+ Pa (p) = kg/kg '
    elif out_type == 'mixing ratio':
        Pd = p - e
        out = (e / Pd) * c
        out_unit = '+ Pa (p) = 1 '
    elif out_type == 'ppmv':
        Pd = p - e
        out = (e / Pd) * 1e6
        out_unit = '+ Pa (p) = ppmv'
    elif out_type == 'relative humidity':
        es = esat(t, method=method)
        out = 100. * e / es
        out_unit = '+ K (t) = %'
    elif out_type == 'virtual temperature':
        out = t / (1 - (e / p) * (1 - c))
        out_unit = '+K (t) + Pa (p) = K'
    elif out_type == 'dew point':
        out = dewpoint(e, method=method)
        out_unit = 'K'
    else:
        print "[OUTPUT] Unknown Conversion"
        return
    if ispandas:
        if len(out.shape) > 1:
            out = pd.DataFrame(out, index=time, columns=columns)
        else:
            out = pd.Series(out, index=time)
    if nounits:
        return out
    else:
        print "Conversion: %s => %s" % (in_unit, out_unit)
        print in_type, ' => ', out_type
        return out