        Call a function once for each model in the library.

        Similar to the built-in ``map`` function this applies the
        function "function" to each model in the library by iterating
        through the models (yielding on each function call).

        Parameters
        ----------
        function : callable
            A function that accepts 2 arguments, ``model`` and ``index``

        modify : bool, optional, default=True
            For an "on_disk" library, temporary files will only be written
            when modify is True. For a library that is not "on_disk"
            this option has no effect and any modifications made to the model
            while it was borrowed will persist.

        Returns
        -------
        result_iter : generator
            A generator that will return function results. This can be
            converted to a list ``list(result_iter)`` to get the results
            of all the function calls (ordered the same as the models in
            the library).


        Determine the "filename" for a model. This will be used
        when writing temporary files (if the library is "on_disk")
        and for the ``save`` method (see the method for a note about
        how this is not used for the pipeline code).

        By default this method will return ``model.meta.filename``
        or "model.asdf" (if ``model.meta.filename`` is None).

        Parameters
        ----------
        model : DataModel

        Returns
        -------
        filename : str


        Compute "exptype" from a model using the DataModel interface.

        This will be called for every model in the library:
            - when the library is created from a list of models
            - when _save is called
        In both cases the models are all in memory and this method
        can use the in memory DataModel to determine the "exptype"
        (likely ``model.meta.exptype``).

        Parameters
        ----------
        model : DataModel

        Returns
        -------
        exptype : str
            Exposure type (for example "SCIENCE").


        Return the name of the observatory as a string

        Returns
        -------
        observatory : str


        Open a model from a filename

        Parameters
        ----------
        filename : str or Path
            Filename from which to load a model.

        **kwargs : dict, optional
            Arguments to be passed to any lower-level function that
            opens a model.


        Load an association from a filename

        Parameters
        ----------
        filename : str or Path
            Filename from which to load an association


        Compute a "group_id" for a DataModel in filename.

        This will be called for every member in the association
        when the library is created if the member entry does not
        contain a "group_id" (this is the most efficient mode).
        Ideally this method should avoid opening the filename as
        a DataModel and instead take "short-cuts" to read only
        the "group_id" (from FITS or ASDF headers).

        If no "group_id" can be determined `NoGroupID` should be
        raised (to allow the library to assign a unique "group_id").

        Parameters
        ----------
        filename : str or Path
            Filename containing a DataModel

        Returns
        -------
        group_id : str
            "group_id" (used for ``group_names`` and ``group_indices``)
            for the model in the provided filename.


        Compute a "group_id" from a model using the DataModel interface.

        This will be called for every model in the library:
            - when the library is created from a list of models
            - when _save is called
        In both cases the models are all in memory and this method
        can use the in memory DataModel to determine the "group_id"
        (likely ``model.meta.group_id``).

        If no "group_id" can be determined `NoGroupID` should be
        raised (to allow the library to assign a unique "group_id").

        Parameters
        ----------
        model : DataModel

        Returns
        -------
        group_id : str
            "group_id" (used for ``group_names`` and ``group_indices``)
            for the model in the provided filename.


Tailor the CRDS core library getreferences() call to the stpipe code by
    adding locking and truncating expected exceptions.   Also simplify 'NOT FOUND n/a'
    to 'N/A'.  Re-interpret empty reference_file_types as "no types" instead of core
    library default of "all types."


Verify that `refpath` exists and is readable for the current user.

    Ignore reference path values of "N/A" or "" for checking.


Convert an abstract CRDS reference file URI into an absolute path for the
    file as located in the CRDS cache.

    Parameters
    ----------

    reference_uri :  string identifying an abstract CRDS reference file,
                      .e.g. 'crds://jwst_miri_flat_0177.fits'

    observatory : string naming the telescope/project for CRDS, e.g. 'jwst', 'roman'

    Returns
    -------

    reference_path : absolute file path to reference_uri in the CRDS cache,
           .e.g. '/grp/crds/cache/references/jwst/jwst_miri_flat_0177.fits'

    Standard CRDS cache paths are typically defined relative to the CRDS_PATH
    environment variable.  See https://jwst-crds.stsci.edu guide and top level
    page for more info on configuring CRDS.

    The default CRDS_PATH value is /grp/crds/cache, currently on the Central Store.


    Parse CLI arguments and run the command.  Does not catch exceptions.

    Parameters
    ----------
    raw_args : list of str
        Command-line arguments (excluding the "stpipe" command itself).

    Returns
    -------
    int
        Exit status.


    Main function for stpipe CLI.  Registered with the console_scripts
    entry point as 'stpipe'.  Also called from stpipe.__main__.

    Raises
    ------
    SystemExit
        In all scenarios.


    Print stpipe version as well as versions of any packages
    that register an stpipe.steps entry point.


        Add this command's parser to the stpipe subparsers.

        Parameters
        ----------
        subparsers : argparse._SubParsersAction


        Run the command with the specified arguments.

        Parameters
        ----------
        args : argparse.Namespace
            Parsed arguments.

        Returns
        -------
        int
            Exit status code.


    Run Steps from the command line

    Exit Status
    -----------
        0:  Step completed satisfactorily
        1:  General error occurred

    Other status codes are Step implementation-specific.


replace zeros by Inf


Call signatures::

    readfield(filename, dims, numpy.datatype)

    Read unblocked binary data with dimentions "dims".


Call signatures::

    writefield(filename, numpy.ndarray)

    Write unblocked binary data.


 v6t = split_C_cub(v3d)
    --------------------------------------------
    split 2d/3d arrays V, center, to 2d/3d x 6 faces
    and add 1 column + 1 row <== at the begining !!!
    => output is v6t[nr,ny+1,ny+1,6]


calculate gradient of 6-tiled fields fld[nr,ny+1,ny+1,6]
    and return as (dfx[nr,ny,ncx], dfy[nr,ny,ncx])


For each of the terms in fldLst
      a) print some stats of this term
      b) add to other tendency and print stats of the sum
      c) substract the sum from total tendency (-> residual) and print stats


    Return a role processor for external links to files based on a URL pattern.

    %s in *pattern* will be replaced by the role text, a file path, with two
    modifications:

    - an explicit title can be specified as for internal sphinx cross
      references: :role:`title <target>` will display *title* but link to a URL
      formed from *target*.
    - if the role text is prefixed with ~, only the last path component will be
      displayed: :role:`~path/to/file` will display *file* but link to
      path/to/file.


    Return a role processor for external links based on a URL pattern.

    %s in *pattern* will be replaced by the role text.


    Computes blanklist for data.exch2

    Parameters
    ----------
    depth      : 2D array_like
                 depth [m].
    sNx        : int
                 x point in each tile.
    sNy        : int
                 y point in each tile.
    tilemap    : bool
                 True : output tile contourplot,
                 default False.

    Returns
    -------
    blank         : list of int
                    empty tiles numbers
    fig(optional) : matplotlib figure
                    tile plot

    Usage
    -----
    >>> blank=gen_blanklist(bathy, 5, 5, tilemap=False)
    10,11,12,..,103
    >>> [blank,fig]=gen_blanklist(bathy, 5, 5, tilemap=True)
    10,11,12,..,103

    Example
    -------
    >>> eg_blanklist()
    10,11,12,..,103


    Computes hFacC,W,S

    Parameters
    ----------
    depth      : 2D array_like
                 Depth [m].
    rF         : 1D array_like
                 Depth at the f point.
    hFacMin    : float
                 Min fraction for partial vertical levels.
    hFacMinDr  : float
                 Min depth for partial vertical levels.
    htype      : string
                 Types of hfac: one or more of 'C','S','W', default='C'.

    Returns
    -------
    hFacC,W,S : tuple of array_like
                The hfac arrays requested in htype.
    Usage
    -----
    >>> [hFacC]=mit.hfac(depth,rF,0.3,50,'C')

    Example
    -------
    >>> [hFacC]=eg_hfac()

    Notes
    -----

    The first row and column are filled with zeros
    for the hFacS and hFacW, respectively.


    Read meta-data files as written by MITgcm.

    Parameters
    ----------
    fname : string
        name of file to read
    ndims : int
        dimension of the file
    dataprec : string
        precision of resulting file ('float32' or 'float64')
    machineformat : string
        endianness ('b' or 'l', default 'b')

    Returns
    -------
    arr : array_like
          numpy array of the data read

    Usage
    -----
    >>> arr=readbin('bathy.bin',[Y,X])


    Pseudocolor plot of land mask with tiles superimposed, optionally
    showing the values of arr for a single tile.

    Parameters
    ----------
    arr        : 2D array_like
                 values to plot, land mask is taken as arr==fill_value
    sNx        : int
                 number of x points in each tile
    sNy        : int
                 number of y points in each tile
    tilen      : int or None
                 plot a specific tile, default None
    sel_zoom   : int
                 zooming range, default 5
    fill_value : float
                 default 0

    Returns
    -------
    figure     : matplotlib figure
                 Plot of land mask, tiles and arr values

    Usage
    -----
    >>> [fig]=tilecmap(bathy, 5, 5)
    >>> [fig]=tilecmap(bathy, 5, 5, 66, sel_zoom=4)

    Example
    -------
    >>> eg_tilemap()


Write an array to a bin format for MITgcm

    Parameters
    ----------
    fbase : string
            Name of file to write
    arr : array_like
          Numpy array to write
    dataprec : string
               precision of resulting file ('float32' or 'float64')
               ('float32' by default)
    machineformat : string
                    'b' or 'l' for big or little endian
                    ('b' by default)
    Usage
    -----
    >>> writebin('data.bin',arr)


    Check compatibility of dimensions of input variables and

    Parameters
    ----------
    salt : array_like
        salinity [psu (PSS-78)]
    theta : array_like
        potential temperature [degree C (IPTS-68)]
        same shape as salt
    p  : pressure [dBar]


    Computes in-situ density of water

    Density of water using the linear EOS of McDougall (1987).

    Parameters
    ----------
    salt : array_like
        salinity [psu (PSS-78)]
    theta : array_like
        potential temperature [degree C (IPTS-68)]
        same shape as salt
    sref  : reference  salinity
            default 30 [psu (PSS-78)]
    tref  : reference potential temperature
            default 20 [degree C (IPTS-68)]
    sbeta  : haline expansion coefficient
             default 7.4e-04 [1/C]
    talpha    : therma expansion coefficient
              default 2.0e-04 [(g/Kg)-1]
    rhonil    : density of water
              default 999.8 [(g/Kg)-1];

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> dens.linear(35.5, 3.)
    1007.268506

    Notes
    -----
    - Source code written by Martin Losch 2002-08-09
    - Converted to python by Gavilan on 2024-07-18


    Calculates in-situ density as approximated by the POLY3 method
    based on the Knudsen formula (see Bryan and Cox 1972).

    Parameters
    ----------
    poly3 : coefficients read from file
            'POLY3.COEFFS' using INI_POLY3
    salt : array_like
           salinity [psu (PSS-78)]
    theta : array_like
            potential temperature [degree C (IPTS-68)];
            same shape as salt

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> p=ini_poly3()
    >>> T=rdmds('T',100)
    >>> S=rdmds('S',100)
    >>> D=poly3(p,salt,theta)
    >>> or to work within a single model level
    >>> D=poly3(P[3,:],S[3,:,:],T[3,:,:])

    Notes
    -----
    - Source code written by Martin Losch 2002-08-09
    - Converted to python by Gavilan on 2024-07-18


Reads the file fpath (default 'POLY3.COEFFS') and returns
    coefficients in poly


    Computes in-situ density of sea water

    Density of Sea Water using Jackett and McDougall 1995 (JAOT 12)
    polynomial (modified UNESCO polynomial).

    Parameters
    ----------
    salt : array_like
           salinity [psu (PSS-78)]
    theta : array_like
        potential temperature [degree C (IPTS-68)];
        same shape as s
    p : array_like
        sea pressure [dbar]. p may have dims 1x1,
        mx1, 1xn or mxn for s(mxn)

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> dens.jmd95(35.5, 3., 3000.)
    1041.83267

    Notes
    -----

    - Jackett and McDougall, 1995, JAOT 12(4), pp. 381-388
    - Source code written by Martin Losch 2002-08-09
    - Converted to python by jahn on 2010-04-29


Compute bulk modulus


    Computes in-situ density of sea water

    Density of Sea Water using Fofonoff and Millard (1983)
    polynomial.

    Parameters
    ----------
    salt : array_like
           salinity [psu (PSS-78)]
    theta : array_like
        potential temperature [degree C (IPTS-68)];
        same shape as s
    p : array_like
        sea pressure [dbar]. p may have dims 1x1,
        mx1, 1xn or mxn for s(mxn)

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> dens.unesco(35.5, 3., 3000.)
    1041.87663

    Notes
    -----
    - Source code written by Martin Losch 2002-08-09
    - Converted to python by Gavilan on 2024-07-18


    Computes in-situ density of sea water

    Density of Sea Water using the McDougall et al. 2003 (JAOT 20)
    polynomial.

    Parameters
    ----------
    salt : array_like
        salinity [psu (PSS-78)]
    theta : array_like
        potential temperature [degree C (IPTS-68)];
        same shape as salt
    p : array_like
        sea pressure [dbar]. p may have dims 1x1,
        mx1, 1xn or mxn for salt(mxn)

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> dens.mdjwf(35.5, 3., 3000.)
    1041.83305

    Notes
    -----
    - McDougall et al., 2003, JAOT 20(5), pp. 730-741
    - Converted to python by Gavilan on 2024-07-18


    Computes in-situ density of sea water

    Density of Sea Water using TEOS-10.

    Parameters
    ----------
    salt  : array_like
            absolute salinity [g/kg]
    theta : array_like
            conservative temperature [degree C (IPTS-68)];
            same shape as s
    p : array_like
        sea pressure [dbar]. p may have dims 1x1,
        mx1, 1xn or mxn for s(mxn)

    Returns
    -------
    dens : array
        density [kg/m^3]

    Example
    -------
    >>> dens.teos10(35.5, 3., 3000.)
    1041.70578

    Notes
    -----
    - Converted to python by Gavilan on 2024-07-18


    Map tracer number (1..3843) to 2-character I/O label:

    | 1..99      =>  01..99
    | 100..619   =>  0a..0Z,1a..9Z
    | 620..3843  =>  aa..ZZ

    Parameters
    ----------
    i : int
        ptracer number (1..3843)

    Returns
    -------
    string
        2-character I/O label


Map 2-character IO label to tracer number, the inverse of iolabel()


    Read one or more variables from an mnc file set.

    Parameters
    ----------
    fpatt : string
        glob pattern for netcdf files comprising the set
    varnames : list of strings, optional
        list of variables to read (default all)
    iters : list of int, optional
        list of iterations (not time) to read
    slices : tuple of slice objects
        tuple of slices to read from each variable
        (typically given as numpy.s_[...])

    Returns
    -------
    dict of numpy arrays
        dictionary of variable arrays

    Example
    -------
    >>> S = rdmnc("mnc_*/state.0000000000.*', ['U', 'V'], slices=numpy.s_[..., 10:-10, 10:-10])
    >>> u = S['U']
    >>> v = S['V']

    Notes
    -----
    Can currently read only one file set (i.e., 1 file per tile),
    not several files split in time.

    Consider using mnc_files for more control (and similar convenience).
    The same restriction about multiple files applies, however.


    Computes pressure (dbar) of sea water from depth.

    Parameters
    ----------
    rC : float or array_like
        Depth at c point [m].
    rF0 : float or array_like
        Depth at rF[k=0], default 0.
    lat : array_like or None
        Latitude to compute unesco gravity.  If None, use gravity = 9.81.
        Default None.
    rhoConst : float
        Density of seawater, default 1027.5.
    eosRefP0 : float
        EOS reference pressure (Pa), default 1.01325e+5.
    top_Pres : float
        Reference pressure at the top, default 0.
    surf_pRef : float
        Surface pressure (Pa), default 1.01325e+5.

    Returns
    -------
    p : array_like
        Pressure [dbar].  If rC and lat are both 1-dimensional, a 2-dimensional
        array corresponding to the outer product will be returned.

    Example
    -------
    >>> pfromz(-1000)
    1007.9775
    >>> pfromz([-100,-1000])
    100.7978, 1007.9775
    >>> pfromz([-100,-1000],lat=90)
    101.0256, 1010.2562
    >>> pfromz(-1000,lat=[70,90])
    1009.6304, 1010.2562


    statsPerLayer,statsVertInt,itrs = readstats(fname)

    Read a diagstats text file into record arrays (or dictionaries).

    Parameters
    ----------
    fname : string
        name of diagstats file to read

    Returns
    -------
    statsPerLayer : record array or dict of arrays
        statistics per layer, shape (len(itrs), len(nReg), Nr, 5)
    statsVertInt  : record array or dict of arrays
        column integrals, shape (len(itrs), len(nReg), 5)
    itrs : list of int
        iteration numbers found in the file

    Notes
    -----
    - The 5 columns of the resulting arrays are
      average, std.dev, min, max and total volume.
    - There is a record (or dictionary key) for each field found in the file.
    - Regional axis is omitted if nReg == 1


if iterable, turn into list, otherwise put into list


    Read meta-data files as written by MITgcm.

    Call signatures:

        a = rdmds(fname,...)

        a,its,meta = rdmds(fname,...,returnmeta=True)

    Parameters
    ----------
    fname : string
        name of file to read, without the '.data' or '.meta' suffix.  If itrs is
        given, the iteration number is added to `fname` as well.  `fname` may
        contain shell wildcards, which is useful for tile files organized into
        directories, e.g.,

          T = rdmds('prefix*/T', 2880)

        will read prefix0000/T.0000002880.*, prefix0001/T.0000002880.*, ...
        (and any others that match the wildcard, so be careful how you name things!)

    itrs : int or list of ints or np.nan or np.inf
        Iteration number(s).  With itrs=-1, will try to read

          fname.meta or fname.001.001.meta, ...

        If itrs is a list of integers of an integer, it will read the corresponding

          fname.000000iter.meta, ...

        If itrs is np.nan, it will read all iterations for which files are found.
        If itrs is np.inf, it will read the highest iteration found.

    machineformat : int
        endianness ('b' or 'l', default 'b')
    rec : list of int or None
        list of records to read (default all)
        useful for pickups and multi-field diagnostics files
    fill_value : float
        fill value for missing (blank) tiles (default 0)
    astype : data type
        data type to return (default: double precision)
        None: keep data type/precision of file
    region : tuple of int
        (x0,x1,y0,y1) read only this region (default (0,nx,0,ny))
    lev : list of int or tuple of lists of int
        list of levels to read, or, for multiple dimensions
        (excluding x,y), tuple(!) of lists (see examples below)
    usememmap : bool
        if True, use a memory map for reading data (default False)
        recommended when using lev, or region with global files
        to save memory and, possibly, time

    Returns
    -------
    a : array_like
        numpy array of the data read
    its : list of int
        list of iteration numbers read (only if returnmeta=True)
    meta : dict
        dictionary of metadata (only if returnmeta=True)

    Examples
    --------
    >>> XC = rdmds('XC')
    >>> XC = rdmds('res_*/XC')
    >>> T = rdmds('T.0000002880')
    >>> T = rdmds('T',2880)
    >>> T2 = rdmds('T',[2880,5760])
    >>> T,its = rdmds('T',numpy.inf)
    >>> VVEL = rdmds('pickup',2880,rec=range(50,100))
    >>> a5 = rdmds('diags',2880,rec=0,lev=[5])
    >>> a = rdmds('diags',2880,rec=0,lev=([0],[0,1,5,6,7]))
    >>> from numpy import r_
    >>> a = rdmds('diags',2880,rec=0,lev=([0],r_[:2,5:8]))  # same as previous
    >>> a = rdmds('diags',2880,rec=0)[0, [0,1,5,6,7], ...]  # same, but less efficient
    >>> a = rdmds('diags',2880)[0, 0, [0,1,5,6,7], ...]     # even less efficient


Closes the NetCDF file.


        Adds a dimension to the Dimension section of the NetCDF data structure.

        Note that this function merely adds a new dimension that the variables can
        reference.  The values for the dimension, if desired, should be added as
        a variable using `createVariable`, referring to this dimension.

        Parameters
        ----------
        name : str
            Name of the dimension (Eg, 'lat' or 'time').
        length : int
            Length of the dimension.

        See Also
        --------
        createVariable


        Create an empty variable for the `netcdf_file` object, specifying its data
        type and the dimensions it uses.

        Parameters
        ----------
        name : str
            Name of the new variable.
        type : dtype or str
            Data type of the variable.
        dimensions : sequence of str
            List of the dimension names used by the variable, in the desired order.

        Returns
        -------
        variable : netcdf_variable
            The newly created ``netcdf_variable`` object.
            This object has also been added to the `netcdf_file` object as well.

        See Also
        --------
        createDimension

        Notes
        -----
        Any dimensions to be used by the variable should already exist in the
        NetCDF data structure or should be created by `createDimension` prior to
        creating the NetCDF variable.


        Perform a sync-to-disk flush if the `netcdf_file` object is in write mode.

        See Also
        --------
        sync : Identical function


Returns whether the variable has a record dimension or not.

        A record dimension is a dimension along which additional data could be
        easily appended in the netcdf data structure without much rewriting of
        the data file. This attribute is a read-only property of the
        `netcdf_variable`.


Returns the shape tuple of the data variable.

        This is a read-only attribute and can not be modified in the
        same manner of other numpy arrays.


        Assign a scalar value to a `netcdf_variable` of length one.

        Parameters
        ----------
        value : scalar
            Scalar value (of compatible type) to assign to a length-one netcdf
            variable. This value will be written to file.

        Raises
        ------
        ValueError
            If the input is not a scalar, or if the destination is not a length-one
            netcdf variable.


        Return the typecode of the variable.

        Returns
        -------
        typecode : char
            The character typecode of the variable (eg, 'i' for int).


        Return the itemsize of the variable.

        Returns
        -------
        itemsize : int
            The element size of the variable (eg, 8 for float64).


Example blanklist generator


Example tilemap plot distribution


Example grid mask generator


    Create a contourf plot of a 2-D llc array (with tricontour).

    Call signatures::

        contourf(X, Y, C, N, **kwargs)

        contourf(X, Y, C, V, **kwargs)

    Parameters
    ----------
    X : array-like
        x coordinates of the grid points

    Y : array-like
        y coordinates of the grid points

    C : array-like
        array of color values.

    N : int
        number of levels

    V : list of float
        list of levels

    kwargs
        passed to tricontour.


    Create a contour plot of a 2-D llc array (with tricontour).

    Call signatures::

        contour(X, Y, C, N, **kwargs)

        contour(X, Y, C, V, **kwargs)

    Parameters
    ----------
    X : array-like
        x coordinates of the grid points

    Y : array-like
        y coordinates of the grid points

    C : array-like
        array of color values.

    N : int
        number of levels

    V : list of float
        list of levels

    kwargs
        passed to tricontour.


convert mds data into global 2D field
    only fields with 2 to 5 dimensions are allowed


convert mds 2D data into global 2D field


convert global 2D 'flat field' to mds 2D data


convert global 'flat' field into mds data;
    only fields with 2 to 5 dimensions are allowed


convert mds multidimensional data into a list with 6 faces


convert 6 faces to mds 2D data,
    inverse opertation of llc.faces


convert mds 2D data into a list with 6 faces


    Create a pseudo-color plot of a 2-D llc array (with plt.pcolormesh).

    Call signatures::

        pcol(X, Y, C, **kwargs)

        pcol(X, Y, C, m, **kwargs)

    Parameters
    ----------
    X : array-like
        x coordinates of the grid point corners (G-points)

    Y : array-like
        y coordinates of the grid point corners (G-points)

    C : array-like
        array of color values.

    m : Basemap instance, optional
        map projection to use.
        NOTE: currently not all projections work

    kwargs
        passed to plt.pcolormesh.


Retrieve dimensions of input fields and do some sanity checks


    Compute divergence of vector field (U,V) on llc grid

    Call signatures::

       divergence = div(U, V, DXG, DYG, RAC, HFW, HFS)
       divergence = div(U, V)
       divergence = div(U, V, DXG, DYG)
       divergence = div(U, V, DXG, DYG, RAC)
       divergence = div(U, V, DXG, DYG, hfw=HFW, hfs=HFS)

    Parameters
    ----------
    u   : array-like (timelevel,depthlevel,jpoint,ipoint)
          x-component of vector field at u-point

    v   : array-like (timelevel,depthlevel,jpoint,ipoint)
          y-component of vector field at v-point

    dxg : array-like (jpoint,ipoint), optional
          grid spacing in x across v-point, defaults to one

    dyg : array-like (jpoint,ipoint), optional
          grid spacing in y across u-point, defaults to one

    rac : array-like (jpoint,ipoint), optional
          grid cell area, defaults to dxg*dyg

    hfw : array-like (depthlevel,jpoint,ipoint), optional
          hFac at u-point, defaults to one

    hfs : array-like (depthlevel,jpoint,ipoint), optional
          hFac at v-point, defaults to one


    Average vector component (u,v) to center points on llc grid

    Call signatures::

       uc,vc = uv2c(U,V)

    Parameters
    ----------
    U   : array-like (timelevel,depthlevel,jpoint,ipoint)
          x-component of vector field at u-point

    V   : array-like (timelevel,depthlevel,jpoint,ipoint)
          y-component of vector field at v-point


    Compute horizontal gradient of scalar field X on llc grid

    Call signatures::

       dXdx, dXdy = div(X, DXC, DYC, HFW, HFS)
       dXdx, dXdy = div(X)
       dXdx, dXdy = div(X, DXC, DYC)
       dXdx, dXdy = div(X, hfw=HFW, hfs=HFS)

    Parameters
    ----------
    X   : array-like (timelevel,depthlevel,jpoint,ipoint)
          scalar field at c-point

    dxc : array-like (jpoint,ipoint), optional
          grid spacing in x across u-point, defaults to one

    dyc : array-like (jpoint,ipoint), optional
          grid spacing in y across v-point, defaults to one

    hfw : array-like (depthlevel,jpoint,ipoint), optional
          hFac at u-point, defaults to one

    hfs : array-like (depthlevel,jpoint,ipoint), optional
          hFac at v-point, defaults to one


    Plots 2D scalar fields on the MITgcm cubed sphere grid with pcolormesh.

    Parameters
    ----------
    x : array_like
        'xg', that is, x coordinate of the points one half grid cell to the
        left and bottom, that is vorticity points for tracers, etc.
    y : array_like
        'yg', that is, y coordinate of same points
    data : array_like
        scalar field at tracer points
    projection : Basemap instance, optional
        used to transform if present.
        Unfortunatly, cylindrical and conic maps are limited to
        the [-180 180] range.
        projection = 'sphere' results in a 3D visualization on the sphere
        without any specific projection. Good for debugging.

    Example
    -------
    >>> from mpl_toolkits.basemap import Basemap
    >>> import MITgcmutils as mit
    >>> import matplotlib.pyplot as plt
    >>> from sq import sq
    >>>
    >>> x=mit.rdmds('XG'); y=mit.rdmds('YG'); e=mit.rdmds('Eta',np.inf)
    >>> fig = plt.figure();
    >>> mp = Basemap(projection='moll',lon_0 = 0.,
    >>>              resolution = 'l', area_thresh = 1000.)
    >>> plt.clf()
    >>> h = mit.cs.pcol(x,y,sq(e), projection = mp)
    >>> mp.fillcontinents(color = 'grey')
    >>> mp.drawmapboundary()
    >>> mp.drawmeridians(np.arange(0, 360, 30))
    >>> mp.drawparallels(np.arange(-90, 90, 30))
    >>> plt.show()


output to enable next button after a site has been selected


this is a sample function!


use the model name to determine what model type it is


 Method to check inputs and lookup parameters based on location.
    Generates Markdown text (based on theme) and updates the parameters for the
    model.
    @param [pt]: list or tuple of point coordinates in latitude / longitude (x,y)
    @param [mapTheme]: name of map theme.


 lookup a raster value at a given point. Currently, only works for single-band
    rasters, behaviour for multi-band or time-enabled uncertain.


 get the great circle distance from two lat/long coordinate pairs
    using the Haversine method (approximation)


return the list of layers to search based on the map theme


open the layer and search through the candidate matches
    to find the true intersection with the point.


 find features in the supplied layers that intersect the provided point
    @param [pt]: list or tuple of point coordinates in latitude / longitude (x,y)
    @param [lyrs]: list or tuple of polygon layers to find the point


 find the closest point or line to the supplied point
    @param [pt]: list or tuple of point coordinates in latitude / longitude (x,y)
    @param [closestLayers]: list of point or line layers
    @param [kd_path]: is the path and base name for the KD file stored outside
    of a zipped archive


Construct the URL for the EIA web page listing fuel rates
    using the provided state abbreviation


generate the markdown to be returned for the current theme


takes the results of the lookups, calculates distances, and puts it all in a dictionary


Fetch water utility rates from the NREL API
    using the provided coordinates


converts some string values to their literal values


    returns dict containing dynamic file names that are created
    by interpolating solar, desal and finance model names


Fetch water utility rates from the open_ei API
    using the provided coordinates


    checks lists to see if a key value exists in it
    returns the list and index of the first dict where the key and
    value was found, else returns None,None

    none: index 0 can be returned, so use explicit tests with result


    searches a list to see if a dict with a key value exists in it
    returns the index of the first dict where the key and
    value pair is found, else returns None

    none: index 0 can be returned, so use explicit tests with result


    updates dict in JSON file
    @data dict: data to update json dict
    @filename str: JSON file path containing dict to update


    create a new JSON file with data
    @data JSON data: to initialize file with
    @ filename str: path of file


    returns False if dict is not found in array
    otherwise returns array index
    note: index 0 can be returned, so use explicit tests with result


return all keys from an array of dicts


 loads data based on the chosen theme after a user selects a
    different theme from the dropdown


 if the dropdown is not the same as the title text,
    we need to reload the map with the new choice. Dropdown
    is supplied with callback regardless of status (updated
    or not)


 helper method to return the markdown text relevant for the given
    map theme


pulls properties from dataframe and updates markdown div


 helper method to write out parameters. Uses the solar dataframe point ID
    to write out map paramers to


    After all 3 models are selected updates app JSON file and
    creates button to navigate to model variables page


callback for feature hover


filter the Texas water data and City price data based on model or factor price


returns dataframe aggregated by selected time value


update the solar figure object


update the desal figure object


    @model_variable_lists = list of model variable dicts
        to pull tabs from
    Returns sorted unique tabs list


    for the provided tab, collects all variables under
    the same section+subsection combination
    and creates the corresponding model variable tables


    @json_vars: string containing path to json model variables file
    @json_vals: string containing path to json model values file
    opens and loads json variable and value files,
    matches up variables to values,
    cleans up the values, removing spaces
    sorts the values by hierarchy
    returns: a list of default dicts


runs solar thermal desal system with financial model


    Titles the collapse buttons based on values stored in JSON file
    For the models selected, figures out the page in our documentation
    to point the user to and returns the link to that page


    reads app json and opens alert if parametric set to true
    Not activated for parametric study and static collector models


    Once someone is done editing the tables they hit the Run Model button
    This triggers the callback.
    We then check through the state of each table to see if it has been
    edited. We can tell by whether or not it has a data_timestamp.
    If it has been edited we update the model variables dict which will be
    converted to json and used as input to run the model.
    Finally the model is run.


initial callback to gather data for callbacks chained below
    updates app_json dict with all values needed for analysis report


    Thermal conductivity of seawater accounting for pressure dependency
    VALIDITY: (1) 10 < T < 90 C; 0 < S < 120 g/kg;  P = P0
              (2) 10 < T < 60 C; 0 < S < 35 g/kg; 0.1 < P < 12 MPa

    ACCURACY: (1) 2.59%
              (2) 2.59%


Density of seawater, Zhuoran's transcription


    Saturated vapor pressure of seawater, Zhuoran's transcription
    returns saturated vapor pressure in N/m^2 (Pa)


Latent heat of seawater, Zhuoran's transcription


Specific heat of seawater, Zhuoran's transcription


Send a request to the server \n \
           server = address of server \n \
           app      = application name \n \
           aline  = line to send to server \n \
           disp = Print output \n


Load APM model file \n \
           server   = address of server \n \
           app      = application name \n \
           filename = APM file name


Load CSV data file \n \
           server   = address of server \n \
           app      = application name \n \
           filename = CSV file name


Retrieve restart file \n \
           server   = address of server \n \
           app      = application name \n \
           mode = {'ss','mpu','rto','sim','est','ctl'}


Open APM web viewer in local browser \n \
           server   = address of server \n \
           app      = application name


Open APM root folder \n \
           server   = address of server \n \
           app      = application name


Classify parameter or variable as FV, MV, SV, or CV \n \
           server   = address of server \n \
           app      = application name \n \
           type     = {FV,MV,SV,CV} \n \
           aline    = parameter or variable name


Load CSV File into Python
           A = csv_data(filename)

           Function csv_data extracts data from a comma
           separated value (csv) file and returns it
           to the array A


Lookup Index of CSV Column \n \
           name     = parameter or variable name \n \
           replay   = csv replay data to search


Retrieve CSV Element \n \
           name     = parameter or variable name \n \
           row      = row of csv file \n \
           replay   = csv replay data to search


Transfer measurement to server for FV, MV, or CV \n \
           server   = address of server \n \
           app      = application name \n \
           name     = name of {FV,MV,CV}


     APM Solver for simulation, estimation, and optimization with both
      static (steady-state) and dynamic models. The dynamic modes can solve
      index 2+ DAEs without numerical differentiation.

     y = solve(app,imode,web_option=False)

     Function solve uploads the model file (apm) and optionally
       a data file (csv) with the same name to the web-server and performs
       a forward-time stepping integration of ODE or DAE equations
       with the following arguments:

      Input:      app = model (apm) and data file (csv) name
                imode = simulation mode {1..7}
                                   steady-state  dynamic  sequential
                        simulate     1             4        7
                        estimate     2             5        8
                        optimize     3             6        9
           web_option = open web-viewer

     Output: y.names  = names of all variables
             y.values = tables of values corresponding to y.names
             y.nvar   = number of variables
             y.x      = combined variables and values but variable
                          names may be modified to make them valid
                          characters (e.g. replace '[' with '')


     Identification of linear time-invariant models

     y = sysid(data,ni,nu,nu)

     Function sysid breaks up data into individual elements including:
       column 0 = time
       column 1-nu = inputs
       column nu+1-nu+ny = outputs

      Input:    data = data for the regression
                ni   = number of inputs
                nu   = number of input coefficients
                ny   = number of output coefficients

     Output:    returns ypred (predicted outputs)
                sysa.apm is written (model file with identified parameters)
                There is optionally a plot and other output that appears
                when flag "fast" is set to False


    The plotter will go through each of the variables in the output y and
      create plots for them. The number of vertical subplots can be
      specified and the plots can be saved in the same folder.

    This functionality is dependant on matplotlib, so this library must
      be installed on the computer for the automatic plotter to work.

    The input y should be the output from the apm solution. This can be
      retrieved from the server using the following line of code:
      y = get_solution(server, app)


ja will be the json piece that travels through the recursion and builds down to lower levels
    when adding new level insert into 0 position if list exists: a.insert(0, x)


Returns a string of the month-day-year-hour-minute plus extension


    Builds an index for the supplied point geometry.
    Supports geojson and shapefile inputs.
    @param [shp]: full path to shp or geojson file


    Writes out the index to the specified path.
    @param [idx]: rtree object
    @param [fullPath]: Path where object should be written


    Builds an index for the supplied polygon geometry.
    Supports geojson and shapefile inputs.
    @param [shp]: full path to shp or geojson file


Compute distances to pixels in cutout


Cuts out the aperture and defines slice objects.
        General setup procedure.


Fits 1d Moffat function to measured radial profile.

        Fits a moffat profile to the distance and values of the pixels.
        Further development may allow user defined models.


Returns 1D Moffat profile evaluated at r values.

        This function takes radius values and parameters in a simple 1D
        moffat profiles and returns the values of the profile at those
        radius values.  The model is defined as:
        model = amp * (1. + (r / gamma) ** 2.) ** (-1. * alpha) + bias

        Parameters
        ----------
        r : array
            The distances at which to sample the model
        amp : float
            The amplitude of the of the model
        gamma: float
            The width of the profile.
        alpha: float
            The decay of the profile.
        bias: float
            The bias level (piston term) of the data.  This is like a background
            value.

        Returns
        -------
        model : array
            The values of the model sampled at the r values.


Recenters source position in cutout and updates x,y attributes


Makes plot of radial profile

        Plots the radial profile, that is pixel distance vs
        pixel value.  Can plot on an existing axes object if
        the an axes object is passed in via the ax parameter.
        The function attempts to set sensible axes limits, specifically
        half of the smallest positive value (axes are logarithmic).
        The axes object is returned by this, so that parameters can
        be set by the user later.

        Parameters
        ----------
        ax : matplotlib.axes.Axes, optional
            An axes object to plot the radial profile on (for integrating)
            the plot into other figures.  If not set, the script will create
            an axes object.
        show_fit : bool, optional
            Plot the fitted model.  Only done if fit was successful.
        Returns
        -------
        ax : matplotlib.axes.Axes
            The axes object containing the radial profile plot/


Computes photometry with PhotUtils apertures, with IRAF formulae

    Parameters
    ----------
    data : array
        The data for the image to be measured.
    coords : array_like or `~astropy.units.Quantity`, optional
        Pixel coordinates of the aperture center(s) in one of the
        following formats:

            * single ``(x, y)`` tuple
            * list of ``(x, y)`` tuples
            * ``Nx2`` or ``2xN`` `~numpy.ndarray`
            * ``Nx2`` or ``2xN`` `~astropy.units.Quantity` in pixels

        Note that a ``2x2`` `~numpy.ndarray` or
        `~astropy.units.Quantity` is interpreted as ``Nx2``, i.e. two
        rows of (x, y) coordinates.

        NOTE: Either coords or  coord_file must be defined
    coord_file : str, optional
        The name of the file containing the coordinates.  The file
        should should have 2 columns (X and Y), and a row for each
        source.  Lines starting with '#' are skipped.  Do not
        include column names unless those lines start with '#'.
    radius : float, optional
        The radius of the photometric aperture in pixels. Default 10.
    annulus: float, optional
        The inner radius of the background annulus in pixels.
        Default 10.
    dannulus: float, optional
        The width of the background annulus in pixels.
        Default 5.
    salgorithm: {'mean', 'median', 'mode'}, optional
        The statistic used to calculate the background.
        All measurements are sigma clipped.
        NOTE: From DAOPHOT, mode = 3 * median - 2 * mean.
    error_array: array, optional
        The array of pixelwise error of the data.  If none, the
        Poisson noise term in the error computation will just be the
        square root of the flux/epadu. If not none, the
        aperture_sum_err column output by aperture_photometry
        (divided by epadu) will be used as the Poisson noise term.
    epadu : float, optional
        Gain in electrons per adu (only use if image units aren't e-).
    origin : float, optional
        The position of the center of the bottom-left pixel of data.
        The coordinate convention of the package used to find the
        sources dictates what this value should be. If coordinates are
        from DS9, IRAF, or SExtractor, set to 1. If coordinates are
        from PhotUtils (or another 0 indexed coordinate system), leave
        as the default.  Default 0.

    Returns
    -------
    photometry_tbl : astropy.table.Table
        An astropy Table with the colums X, Y, flux, flux_error, mag,
        and mag_err measurements for each of the sources.


Computes mean/median/mode/std in Photutils apertures.

    Compute statistics for custom local background methods.
    This is primarily intended for estimating backgrounds
    via annulus apertures.  The intent is that this falls easily
    into other code to provide background measurements.

    Parameters
    ----------
    data : array
        The data for the image to be measured.
    apertures : photutils PixelAperture object (or subclass)
        The phoutils aperture object to measure the stats in.
        i.e. the object returned via CirularAperture,
        CircularAnnulus, or RectangularAperture etc.
    method: str
        The method by which to handle the pixel overlap.
        Defaults to computing the exact area.
        NOTE: Currently, this will actually fully include a
        pixel where the aperture has ANY overlap, as a median
        is also being performed.  If the method is set to 'center'
        the pixels will only be included if the pixel's center
        falls within the aperture.
    sigma_clip: bool
        Flag to activate sigma clipping of background pixels

    Returns
    -------
    stats_tbl : astropy.table.Table
        An astropy Table with the colums X, Y, aperture_mean,
        aperture_median, aperture_mode, aperture_std, aperture_area
        and a row for each of the positions of the apertures.


Create a WCS for an FLT/FLC sci extension from
    values in row of a DRZ/DRC HDRTAB

    This function takes in a row in a HDRTAB extension
    from a drizzled image and reconstructs the WCS for the
    extension of the exposure corresponding to that row.  See
    make_wcs_list for further information.


    Create list of WCS objects of input exposures/extensions of
    a drizzled image, by reading parameters from DRZ HDRTAB.

    This function regenerates the WCS of input exposures, by
    reading the WCS parameters from the corresponding row in
    the HDRTAB.  This allows recovery of exposure astromertic solutions
    without needing the files of the exposures themselves.
    Furthermore, this ensures consistency of the exposure WCS and the
    drizzled image, as the HDRTAB is created at drizzle runtime.

    NOTE: This does NOT include the look-up table distortions,
    so positions from this WCS may differ from the real WCS by
    a few hundredths of a pixel.

    Parameters
    ----------
    hdrtab : astropy Table
        The HDRTab from the drizzled image file.

    Returns
    -------
    wcs_list : list
        List of WCS objects for each sci extension that
        created drizzled image.


    This function computes how many exposures and seconds cover a
    catalog of positions in a drizzled frame.

    For every position in a catalog corresponding to a drizzled frame,
    this function returns how many exposures covered that point, and
    how many seconds of exposure time covered that point.  It does this
    by reconstructing the WCS of every input exposure/extension, and
    transforming the positions in the catalog to the exposure/extension
    frame, and seeing if the transformed positions land on the array.
    It then adds up the exposure time of each exposure, accounting for
    each exposures coverage of the different positions.  The WCS's are
    reconstructed from the HDRTAB, see make_wcs_list() for details.

    For this to work properly, the drizzled image must be multi extension,
    with a single SCI extension and HDRTAB extension (this is default).
    Furthermore, the catalog must contain columns named 'X' and 'Y',
    which are 1-indexed pixel positions in the drizzled image frame.

    NOTE: As the lookup table distortions are not stored in the HDRTAB,
    the transformed positions are slightly off from the real positions,
    but the errors are small, generally within a few hundredths of a pixel.
    NOTE: This does NOT account for effects like saturation, or guide star
    tracking issues.

    Parameters
    ----------
    drz : str
        Path to drizzled image
    cat : astropy Table
        Catalog containing X and Y positions in drizzled frame

    Returns
    -------
    wcs_list : list
        List of WCS objects for each sci extension that
        created drizzled image.


Computes photometry with PhotUtils apertures, with IRAF formulae

    Parameters
    ----------
    phot_apertures : photutils PixelAperture object (or subclass)
        The PhotUtils apertures object to compute the photometry.
        i.e. the object returned via CirularAperture.
    bg_apertures : photutils PixelAperture object (or subclass)
        The phoutils aperture object to measure the background in.
        i.e. the object returned via CircularAnnulus.
    data : array
        The data for the image to be measured.
    error_array: array, optional
        The array of pixelwise error of the data.  If none, the
        Poisson noise term in the error computation will just be the
        square root of the flux/epadu. If not none, the
        aperture_sum_err column output by aperture_photometry
        (divided by epadu) will be used as the Poisson noise term.
    bg_method: {'mean', 'median', 'mode'}, optional
        The statistic used to calculate the background.
        All measurements are sigma clipped.
        NOTE: From DAOPHOT, mode = 3 * median - 2 * mean.
    epadu: float, optional
        Gain in electrons per adu (only use if image units aren't e-).

    Returns
    -------
    final_tbl : astropy.table.Table
        An astropy Table with the colums X, Y, flux, flux_error, mag,
        and mag_err measurements for each of the sources.


Computes the flux errors using the DAOPHOT style computation


    Breaks up hst1pass catalogs and saves per chip catalogs.

    hst1pass outputs catalogs where the measurements from both chips
    are merged together.  This splits that catalog into 1 catalog for
    each chip, and resets the y coordinate for chip one (in merged
    catalog, chip 1 starts at y=2048, in separate catalogs it starts
    back at 0).  Also computes/adds RA/Dec columns into catalogs

    Parameters
    ----------
    input_catalogs : list
        List of catalogs output from hst1pass.  Typically should be
        the image filename, with '.fits' replaced with '.xympqks'.


    Adds RA/Dec column into table containing x/y columns via WCS.

    Inputs a table <tbl> with x/y values, reads a WCS from image
    <image_name> and transforms the x/y values to RA/DEC values via
    the wcs <wcs_i>.  If wcs_i not given, uses <image_name> and
    <sci_ext> to read in the WCS.  Saves the output table as
    <image_rootname>_fl[ct]_sci<sci_ext>_xyrd.cat.

    Parameters
    ----------
    tbl : astropy.table.Table
        Table containing x and y columns to be transformed
    image_name : str
        Image from which to get the WCS. Should be image that
        tbl was derived from.
    sci_ext : int
        Science extension from which to get the WCS/name the output.
        For UVIS this is either 1 or 2, for IR it is always 1.
    wcs_i : astropy.wcs.WCS or subclass, optional
        WCS object to use for transformation.  If None, the WCS is
        read in from the image_name and sci_ext given.


    Makes the list of catalogs associated with each image for TweakReg

    Makes file containing the appropriate entries for TweakReg to use
    the PSF photometry catalog files.  See the TweakReg docs section
    regarding the 'catfile' parameter for further information.


    Reads the hst1pass file into astropy table.

    Parameters
    ----------
    input_catalog : str
        Catalog output from hst1pass (.xympqks file)

    Returns
    -------
    tbl : astropy.table.Table
        Table containing the columns with appropriate names from
        hst1pass catalog.


Convert sky to int pixel positions in the reference frame


    Recomputes image catalogs' RA/Dec vals. Useful after aligning.

    Aligning images changes the WCS, so the transformation from
    x/y to RA/Dec must be recomputed.  This is a helper function
    to do that for multiple images and the corresponding catalogs.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).  Must be fits files.


    Creates coverage map of input images in reference frame

    Parameters
    ----------
    input_wcss : list
        List of WCS's of science extensions of data.  Should
        include distortion solutions etc.
    ref_wcs : astropy.wcs.WCS
        WCS object for the final reference frame.

    Returns
    -------
    coverage_map : numpy.ndarray
        Array with same dimensions as ref_wcs._naxis, with number
        of images per pixel.


    Calculates a WCS for the final reference frame

    This function is used to calculate the WCS for the final reference
    frame for the photometric catalogs, peak map and coverage map. The
    WCS has the NAXIS keywords set large enough to encompass all input
    images completely.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).

    Returns
    -------
    output_wcs : HSTWCS
        WCS object for the final reference frame. Like an Astropy WCS.


    Performs pixel area correction on magnitude measurements in catalog.

    The PSF magnitudes are measured in the image frame, which does not
    account for the pixel area.  This function stores the pixel area map
    as a set of 2D polynomials, and evaluates the values of those
    polynomials at each x,y in the catalogs.  Finally it applies those
    evaluated values to the magnitude measurements in the catalog.

    Note: Since the table is passed by reference, the corrected column
    does not need to be returned to updated the catalog (it's updated
    in place).

    Parameters
    ----------
    catalog : astropy.table.Table
        Table containing x, y and magnitude measurements
    detchip : str
        Detector/chip string.  I.E chip 1 of wfc3/uvis is 'uvis1'.  If
        detector only has 1 chip, then no number should be added (i.e just
        'ir' for wfc3/ir).
    mag_colname : str
        Name of the column containing the magnitudes to be corrected.
        Default is 'm'.


    Main function to run to do finding/PSF fitting of stars with python engine

    This is the top level function of the python PSF photometry interface.
    This gets the PSF and other information, loops over the images and calls
    the fitting functions.  The inputs control the star finding/rejection
    criteria.  The outputs photometric catalogs are saved as ascii tables.

    Note: Focus dependent PSFs not yet supported in the python engine (but
    are coming soon)

    Parameters
    ----------
    input_images : list
        List of image filenames (strings) to measure.  Must be fits files.
    psf_model_file : str, optional
        Name of fits file containing PSF model.  If None (default),
        finds/downloads the appropriate model from WFC3 website.
    hmin : int, optional
        Minimum separation (in pixels) between peaks for them to be measured.
        Default 5.
    fmin : float, optional
        Minimum flux (in image units) in the central 2x2 pixels for a source
        to be measured. Default 1000.
    pmax : float, optional
        Maximum flux (in image units) of the brightest pixel in a source for
        it to be measured. Default 70000 (saturation threshold).  Setting this
        slightly lower is likely advantageous, as the python interface cannot
        measure saturated UVIS stars well.
    qmax : float, optional
        Maximum fit quality for fit of a given star to be considered good.
        Fit quality is defined as:
        sum(abs((data - sky - fitted_model)/fitted_flux)))
    cmin : float, optional
        Minimum scaled residual of the central pixel for the measurement to be
        considered good.  Scaled residual is defined as:
        (peak pixel value - sky - fit peak pixel value)/fitted_flux.
        This helps reject extended/diffuse sources.  Default -1.
    cmax : float, optional
        Maximum scaled residual of the central pixel for the measurement to be
        considered good (see cmin).  Default 0.1.  Helps reject cosmic rays.
    ncpu : int, optional
        Number of CPUs to use to distribute fitting across.  If None, uses
        all cpus.  Default None.


    Finds and measures stars in data array using the PSF model.

    This is the handler function to do the finding/fitting for stars in
    a single science extension of an image, as well as rejection of poor
    fit sources.

    Parameters
    ----------
    data : `numpy.ndarray`
        Array containing the image data for 1 chip (1 science extension)
    mod : `photutils.psf.models.GriddedPSFModel`
        The model of the PSF across that chip.  See make_models().
    hmin : int, optional
        Minimum separation (in pixels) between peaks for them to be measured.
        Default 5.
    fmin : float, optional
        Minimum flux (in image units) in the central 2x2 pixels for a source
        to be measured. Default 1000.
    pmax : float, optional
        Maximum flux (in image units) of the brightest pixel in a source for
        it to be measured. Default 70000 (saturation threshold).  Setting this
        slightly lower is likely advantageous, as the python interface cannot
        measure saturated UVIS stars well.
    qmax : float, optional
        Maximum fit quality for fit of a given star to be considered good.
        Fit quality is defined as:
        sum(abs((data - sky - fitted_model)/fitted_flux)))
    cmin : float, optional
        Minimum scaled residual of the central pixel for the measurement to be
        considered good.  Scaled residual is defined as:
        (peak pixel value - sky - fit pixel value)/fit flux.
        This helps reject extended/diffuse sources.  Default -1.
    cmax : float, optional
        Maximum scaled residual of the central pixel for the measurement to be
        considered good (see cmin).  Default 0.1.  Helps reject cosmic rays.
    ncpu : int, optional
        Number of CPUs to use to distribute fitting across.  If None, uses
        all cpus.  Default None.

    Returns
    -------
    tbl : `astropy.table.Table`
        Table of fit source positions, magnitudes, sky values, fit qualities,
         and scaled residual of the central pixel.


Helper function to shift around conv kernel for peak finding


Performs filtering/convolution on images for source finding


    Compute sky values around (xs, ys) in data with various parameters

    See photometry_tools.aperture_stats_tbl for more details.


Evaluate the model, and flatten the output


    Fit object at some (x,y) in data array with PSF model

    This is the function that fits each object with the PSF.  It cuts out
    a 5x5 pixel box around the peak of the object, and fits the PSF to that
    cutout.  If it fails, all return values are nans.  Uses curve_fit in
    scipy.optimize for fitting.  The input pixels are given sigmas of
    sqrt(abs(im_data)) for weighting the fit.

    Parameters
    ----------
    xi : int or float
        x position of objects peak, in pixel coordinates.  Can just be the
        integer pixel position.
    yi : int or float
        y position of objects peak, in pixel coordinates.  Can just be the
        integer pixel position.
    bg_est : float
        Sky background level around the object to be subtracted before fitting
    model : `FlattenedModel`
        The GriddedPSFModel, with an evaluate method that returns a flattened
        version of the output (instead of shape being (n,m), get (n*m,))
    im_data : `numpy.ndarray`
        The full image (single chip) data array from which the object should
        be cut out.

    Returns
    -------
    f : float
        The fitted flux of the model
    x : float
        The fitted x position of the model
    y : float
        The fitted y position of the model
    q : float
        The calculated fit quality
    cx : float
        The scaled residual of the central pixel


    Turns pixel coordinates into IDs for each star.

    Each ID is just the X and Y integer pixel postions concatenated.
    For example, (3894, 215) becomes 38940215.  These IDs are then
    used in the matching process.  This will likely be rewritten or
    removed soon in favor of better matching methods.

    Parameters
    ----------
    coord_ints : ndarray
        Nx2 array of coordinates.  Must be integers
    x_digits : int, optional
        Number of digits in the x coordinates.  If none, will
        calculate from largest value.  Necessary for correct
        padding of of ID.
    y_digits : int, optional
        Number of digits in the y coordinates.  If none, will
        calculate from largest value.  Necessary for correct
        padding of of ID.

    Returns
    -------
    ids: list
        List of ids for the source positions from the input coords.


Binary searches array a for element x and returns index


    Matches two final catalogs so each row of the returned tables
    correspond to the same star.

    This function takes in two final catalogs and matches the sources
    listed in them.  This is done by finding closest point (in sky
    space) of in cat2 for every point in cat1.  Points closer than
    max_distance are considered to be the same source. The
    returned tables only contain the sources that were matched.
    Basically just inner joins the tables when matching rows are
    found.

    Parameters
    ----------
    cat1 : astropy.table.Table or str
        The first table (or filename) to be matched
    cat2 : astropy.table.Table or str
        The second table (or filename) to be matched
    max_distance : float, optional
        The threshold (in arcsec) which distances must be in for
        sources to be considered a match.

    Returns
    -------
    matched_cat1 : astropy.table.Table
        The matched version of cat1
    matched_cat2 : astropy.table.Table
        The matched version of cat2


    Matches a single image extension catalog to the master catalog
    so that each row of the returned catalog is the same star

    This function takes in one final catalog and one catalog of a
    single science extension (sci_cat) and matches sources in them.
    This is done by finding closest point in master_cat (in sky space)
    to each point in sci_cat.  Points closer than max_distance are
    considered to be the same source. The returned table contains the
    same number of rows as master_cat, and has values for each of the
    stars successfully matched. Basically just left joins the tables
    when matching rows are found.

    Parameters
    ----------
    master_cat : astropy.table.Table or str
        The master table (or filename) to be matched to
    sci_cat : astropy.table.Table or str
        The single science extension table (or filename) to be matched
    max_distance : float, optional
        The threshold (in arcsec) which distances must be in for
        sources to be considered a match.

    Returns
    -------
    joined : astropy.table.Table
        The matched (left-joined) table.


    Main function for making false star drz/drc

    This function takes in a user supplied drizzled image, and makes an ouput
    image that contains a grid of PSFs as they would be projected in the
    drizzled frame.  The corresponding PSF/input images are determined by
    looking at the header of the drizzled image automatically.

    Parameters
    ----------
    drz : str
        Path to drizzled image to derive frame parameters from.
    input_images : list, optional
        List of the input flt/flc images.  If none, determined from header, but
        the flts/flcs MUST be in the same directory as the drz/drc.  In
        addition, it is critical that the images are well aligned, or the
        output image is not representative of the actual PSF.
    models_only : bool, optional
        Make the output drizzled image only contain the PSF models?  Default
        True (CURRENTLY DOES NOTHING- Ignore)
    input_coordinates : `numpy.ndarray`, optional
        Grid of pixel positions at which to insert the model stars (in drizzle
        frame pixel coordinates).  If none, a grid is automatically generated.
        See _generate_input_coordinates().
    psf_file : str, optional
        Path to file containing PSF models.  If none, automatically determined
        and downloaded using header information of `drz`.

    Returns
    -------
    output_files : list
        List containing the paths to the false star flts/flcs.


Gets cutout of evaluated model, and indices to place cutout


Subtracts the fitted PSF from the positions in catalog


    Reads in PSF model, splits it for multichip data, and makes model objects.

    This function takes a fits file containing a spatially dependent PSF
    (single PSF models at each point in a grid across the detector) and reads
    them into GriddedPSFModel objects that can be used for fitting.  Since the
    PSF model files contain models for both chips (in the case of UVIS) put
    together, this file splits them into the appropriate sections for each
    chip.

    Parameters
    ----------
    psf_file : str
        Name of fits file containing the PSFs

    Returns
    -------
    mod1 : `photutils.psf.models.GriddedPSFModel`
        The gridded PSF model object for the 'SCI, 1' data.
    mod1 : `photutils.psf.models.GriddedPSFModel` or None
        The gridded PSF model object for the 'SCI, 2' data.
        If there is no 'SCI, 2' for that detector (i.e. WFC3/IR), then is None.


    Run TweakReg on the images, using the catalogs from hst1pass.

    Astrometrically align the input images via TweakReg.  Uses the
    catalogs from hstpass as the input positions of the sources.  Can
    optionally align images to a reference frame by giving a reference
    catalog such as Gaia.  For more information, see the TweakReg
    documentation.

    Parameters
    ----------
    input_images : list
        List of image filenames to align using xyrd catalogs (strings).
        Must be fits files.
    reference_catalog : str, optional
        File name of the reference catalog.  If None images are aligned
        to first image in input_images.
    searchrad : float, optional
        Search radius in arcseconds, if not given, uses tweakreg
        default of 1 arcsec.
    gaia : bool
        Align images to Gaia?  If True, queries Gaia in region
        encompassing input images, and saves catalog of Gaia source
        positions, and uses this catalog in TweakReg
    **kwargs : keyword arguments, optional
        Other keyword arguments to be passed to TweakReg.  Examples
        could include minflux, maxflux, fluxunits.  More information
        available at
        https://drizzlepac.readthedocs.io/en/latest/tweakreg.html


    Averages measurements taken from each input image for matched stars

    This function calculates the average and standard deviation of the
    magnitude, RA, Dec, Q parameter, and reference frame X and Y positions
    for each star in the peakmap (that was detected at least the minimum number of
    times).  It also outputs the number of times that star was detected.
    Future enhancements include: making a mbar/mstd column for each filter,
    and adding rejection into computation.

    Parameters
    ----------
    match_arr : numpy.ndarray
        Array with one row for each star, 1 column for each input catalog
        The elements should be the index of the star's row in each input table
        or -1 if the star is not in that input table.
    tbls : list
        List of Astropy tables.  One table for each input catalog.

    Returns
    -------
    final_tbl : astropy.table.Table
        Final averaged photometric catalog.  See the docstring to see
        description of the columns.


    Wrapper for final photometric matching and averaging.

    This function wraps around several utility functions to match,
    organize, and average the hst1pass photometric sources to create
    a final catalog.  It does so by:
    1. projecting all sources detected in the input images
    into a final reference frame creating a map of the detections
    2. Matching sources from the catalogs corresponding to the input
    images
    3. Calculates the statistics of photometric quantities from the
    measurements in the catalogs for each source detected at least
    the number of times specified by the min_detections parameter.
    If saved, the peakmap shows how many times a source was detected
    at certain pixel of the final reference frame in the catalogs.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).  Must be fits files.
    save_peakmap : bool, optional
        Flag to save the map of detections (peakmap).  Default True
    min_detections : int or float, optional
        If int: minimum number of images a source must be detected in
        to be included in the final catalog.
        If float: minimum fraction of images a source must be detected
        in to be included in the final catalog.
        Default is 3.
    drizzle : bool, optional
        Make a drizzled image on the same grid as the reference frame?
        Default False.  The image output from this is not optimized so
        it should only be treated as a simple preview.

    Returns
    -------
    final_catalog : astropy.table.Table
        Final averaged photometric catalog.  See documentation of
        collate() for more information.


    Creates reate the peak map in the reference frame.

    Creates the peak map, that is the number of times a source
    is detected across the catalogs from the input images. The
    image size and orientation is derived from the ref_wcs parameter.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).  Must be fits files.
    ref_wcs : astropy.wcs.WCS
        WCS object to of the reference frame convert sky to pixel
        positions, and get the dimensions of the final reference frame
    save_peakmap : bool, optional
        Flag to save the map of detections (peakmap).  Default True

    Returns
    -------
    peakmap : numpy.ndarray
        The map of source detections
    all_int_coords : list
        List of numpy arrays containing integer coordinates of pixel
        positions in the reference frame.


    Analyzes peaks in the peak map, matches peaks with catalogs, and averages

    Workhorse function for matching and averaging sources from the input
    catalogs.  This function should only be used if having slightly more
    control over the reference frame is desired.  Otherwise, use the
    make_final_table function.

    Parameters
    ----------
    peakmap : numpy.ndarray
        Peak map as described in make_peakmap() returned value
    all_int_coords : list
        List of ndarrays as described in make_peakmap() returned value
    input_cats : list
        List of filenames of catalogs to match/collate.  Order must be
        the same as ordering of all_int_coords
    ref_wcs : astropy.wcs.WCS
        WCS object to of the reference frame convert sky to pixel
        positions, and get the dimensions of the final reference frame
    metas : dict
        Dictionary containing the meta information for each input
        catalog.  Each key is a type of information (such as 'filter'
        or exposure time), and the corresponding value is a list with
        one entry for each of the input catalogs.  Each entry is the
        value of the keyword for the corresponding input catalog.
    min_detections : int, optional
        The minimum number of images a source must be detected in
        to be included in the final catalog

    Returns
    -------
    final_catalog : astropy.table.Table
        Final averaged photometric catalog.  See documentation of
        collate() for more information.


    Naively drizzle the images onto the final wcs grid

    Uses astrodrizzle to combine input images into single stacked
    image.  Uses the coverage map created in create_coverage_map to
    determine the "median depth" of the image (how many images per
    output image pixel)- useful for choosing best algorithm for
    median combine.  Output image is on same pixel grid as the
    image specified by wcs_file parameter.  The coverage map filename
    is the typical input.  This image is not an optimized drizzled
    image, and is meant to give a basic stack.  The drizzled image
    is stored as <FILT>_dr[cz].fits (drc or drz based on input
    images).

    Parameters
    ----------
    images : list
        List of image filenames to drizzle.  Must be fits files.
    coverage_map : numpy.ndarray
        File created via create_coverage_map, i.e. total number of
        input images per output pixel
    wcs_file : string
        File to read WCS from to get the output grid of the drizzled
        image.  Use the filename of the coverage map for simplicity.
    filt : string
        The filter the images were taken with.  Used for naming
        output image


    Run hst1pass.e Fortran code on images to produce initial catalogs.

    This function runs the Fortran routine hst1pass.e, on a set of
    input images.  This is Jay Anderson's PSF fitting single pass
    photometry code.  The fortran code must first be compiled for
    this code to run.  Running this code outputs one catalog for
    each input image, and saves those files to disk.  More parameters
    from the hst1pass.e code may be added to this interface in the
    future.  The original Fortran executable can also be called from
    the command line if desired.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).  Must be fits files.
    hmin : int
        Minimum separation between stars. Default 5
    fmin : int, optional
        The minimum flux (in image units) a source must have to be
        included in the output catalogs. Default 1000.
    pmax : int, optional
        The maximum flux (in image units) a source can have in the
        peak pixel to be included in the output catalogs.  Used to
        filter out saturated sources.  Default 99999.
    out : str, optional
        The measurments to be recorded in the output catalogs.  Each
        character corresponds to one output column.  The default is
        'xympqks' which gives: x coordinate, y coordinate, instrumental
        magnitude, peak pixel value, quality of fit (0 is perfect
        fit), the chip the star was detected on (chip 1 or chip 2
        for UVIS), and the sky value.  If being used with other functions
        in this package x, y, m, q, k, and s must be included in the
        outputs.  More measurements will be supported at a later date.
    executable_path : str, optional
        The path to the hst1pass.e compiled executable.  If None (default),
        the code is assumed to be in the psf_tools directory.

    Returns
    -------
    expected_output_list : list
        List of the output catalogs from running hst1pass


    Makes sure input_file is a valid fits file.

    Tries to open the image to ensure the fits file is readable.
    Good for ensuring the download didn't fail/download garbage

    Parameters
    ----------
    input_file : string
        Filename of fits file to validate


    Checks images to make sure they are wfc3 and one filter.

    Software currently only has full support for WFC3.  Furthermore,
    only a single filter should be passed into most of the functions,
    as the measurements are filter specific.  This function raises an
    exception if those conditions are not met.

    Parameters
    ----------
    input_images : list
        List of image filenames (strings).  Must be fits files.

    Returns
    -------
    filter : str
        Filter name.


    Read the measured focus level from the input catalogs

    If hst1pass was run using focus based PSFs, the focus level for
    each image is stored in the catalog output from hst1pass (the
    .xympqks file).

    Parameters
    ----------
    input_catalogs : list
        List of catalog filenames (strings).

    Returns
    -------
    focus_dict : dict
        Dictionary where dict[input_catalog] = focus level.


Checks the current OS to select correct executable


Returns 1D Moffat profile evaluated at r values.

        This function takes radius values and parameters in a simple 1D
        moffat profiles and returns the values of the profile at those
        radius values.  The model is defined as:
        model = amp * (1. + (r / gamma) ** 2.) ** (-1. * alpha) + bias

        Parameters
        ----------
        r : array
            The distances at which to sample the model.
        amp : float
            The amplitude of the of the model.
        gamma: float
            The width of the profile.
        alpha: float
            The decay of the profile.
        bias: float
            The bias level (piston term) of the data.  This is like a background
            value.

        Returns
        -------
        model : array
            The values of the model sampled at the r values.


Return vertex_indices ordered in an (a, b, c) form where:
      a is the vertex defined by L1 & L2
      b is the vertex defined by L2 & L3
      c is the vertex defined by L3 & L1
    and L1 < L2 < L3 are the sides of the triangle
    defined by vertex_indices.


Return an array of (unique) invariants derived from the array `sources`.
    Return an array of the indices of `sources` that correspond to each
    invariant, arranged as described in _arrangetriplet.


Return a 2D numpy array for an array of arbitrary channels


Return a 2D shape for the image, ignoring channel info


Transform ``source`` to coincide pixel to pixel with ``target``.

    Args:
        source (numpy array): A 2D NumPy, CCData or NDData array of the source
            image to be transformed.
        target (numpy array): A 2D NumPy, CCData or NDData array of the target
            image. Used to set the output image shape as well.
        fill_value (float): A value to fill in the areas of aligned_image
            where footprint == True.
        propagate_mask (bool): Wether to propagate the mask in source.mask
            onto footprint.
        max_control_points: The maximum number of control point-sources to find
            the transformation.
        detection_sigma: Factor of background std-dev above which is considered
            a detection.
        min_area: Minimum number of connected pixels to be considered a source.

    Return:
        A tuple (aligned_image, footprint).
        aligned_image is a numpy 2D array of the transformed source
        footprint is a mask 2D array with True on the regions
        with no pixel information.


        Checks if the pre processing raised an error or not

        Returns
        -------
        status : bool
            True if everything is ok, False if an Error occurred


        Checks if this object contains any data for further processing, otherwise
        raises Exception

        Returns
        -------
        error_code: int
            Code for the error message, see meta dict for message to code
        error_message: str
            Error message for the code


        Checks if in either group are more than the given number of minimum observations

        Parameters
        ----------
        min_obs_n : int
            Number of observations that must be at least in each of the 2 groups

        Returns
        -------
        error_code : int
            Code for the error message thrown here
        error_message : str
            Message for the error in this function
        n0 : int
            Number of observations for the group before the break time
        n1 : int
            Number of observations for the group after the break time


        Check if the correlation of the selected data is above the passed
        thresholds

        Parameters
        ----------
        group_no: int or None
            Number of the group to check (0=before break, 1=after break)
        min_corr : float
            minimum correlation that is necessary
        max_p : float
            significance that is necessary

        Returns
        -------
        error_code : int
            Code for the error message in this function
        error_message : int
            Message for the error in this function
        corr : float
            Spearman correlation for the passed time series
        pval : float
            Significance value for the correlation


        Calls functions for data pre-processing and checking

        Returns
        -------
        error_code_test : int
            Code that identifies which test failed
        error_text_test : str
            Text that describes the problem


Specific for each child class


    Takes the horizontal comparison metrics for a candidate set and compares it to the metric
    for a reference data set via the selected function:

    Parameters
    ----------
    v0 : float
        Value 0 (first in operation)
    v1 : float
        Value 1 (second in operation)
    how : str
        Implemented comparison operation.

    Returns
    -------
    error : float
        The error from comparing the 2 inputs via the comparison method


        Calculate the statistical values needed for comparison within and
        across groups.

        Returns
        -------
        group_stats : pd.DataFrame
            Frame that contains the group stats


        Compare stats within a group.
        We find e.g. the difference in min, max, mean between the candidate and
        reference of each group.

        Returns
        -------
        df_groupstats_compare: pd.DataFrame
            Metric comparison of the groups


        Compare changes in  metrics across the the 2 groups
        via the passed comparison function (usually difference).

        Parameters
        ----------
        df_groupstats_compare : pd.DataFrame
            DataFrame that contains the group stats
        df_validation_metrics : pd.DataFrame
            DataFrame that contains the group metrics
        how : str, optional (default: 'Diff')
            Method how the groups are compared, by default use the difference

        Returns
        -------
        df_metric_change : pd.DataFrame
            Change of metrics between the groups across the break time.


        Calculate vertical metrics between candidate and reference using pytesmo.

        Currently implemented:
            bias, mad, rmsd, nrmsd,
        Returns
        -------
        df_validation_metrics: pd.DataFrame
            Data Frame that contains the metrics between the candidate and reference
            for the 2 groups


        Calculate the measures and compare them over the break time

        Parameters
        ----------
        comparison_method : str, optional (default: AbsDiff)
            How the metrics across the groups are compared. Default
            is the difference between group 1 and group 2.

        Returns
        -------
        df_metric_change : pd.DataFrame
            How the metrics and group stats have changed across the break time.


        Creates a column candidate_flagged with the values in the passed column
        that were filtered with the self.good_flags in 'candidate_flags'.

        Parameters
        -------
        df : pd.DataFrame
            DataFrame that contains a column 'candidate_flags' and that is filtered.
        col_name : str
            Name of the column that is filtered based in the flags.

        Returns
        -------
        ds : pd.Series
            The filtered, selected column


        Creates the check object and runs checks depending on all the passed
        arguments on the frame data.

        Returns
        -------
        input_checkstats : dict
            Dictionary of the input check results and stats


        Drop values in the frame data to fit the coverage of the 2 groups.
        This alters the values in self.df_frame as it removes values there.

        Parameters
        -------
        drop_months : np.array
            List of integers for months that will be removed eg [1,2] for Jan and Feb


        Fetch the plots for the current adjustment method here and append them
        to the bottom of the plot collection like
        # iter1_plotA -- iter1_plotB -- iter1_plotC -- ...
        # iter2_plotA -- iter2_plotB -- iter2_plotC -- ...
            ...             ...             ...


        Initializes the objects for getting correction values

        Parameters
        -------
        perform_bias_corr : bool
            Perform bias correction on the adjustment data (again).
        model_kwargs : dict
            Keyword arguments, that are passed to create the method specific
            object. Are different for each of the implemented methods.

        Returns
        -------
        adjust_obj : RegressPairFit or QuantileCatMatch or HigherOrderMoments
            Object for performing adjustment


        Drop the adjusted values and replace them with the
        original data.
        This is done when the adjustment was performed, but not found successful
        in the output tests.


        This function calculates statistics for ALL the values that are adjusted
        So not the frame data or the flagged data, but the data that is really being adjusted"
        Returns error in cases that the adjustment should not be accepted.

        Parameters
        -------
        bias_diff : bool, optional (default: True)
            Activate to check if the relative bias in the adjusted values
            across the break decreased  relative to the reference data.
        varratio_diff : bool, optional (default: True)
            Activate to check if the difference in variance ratios between the
            candidate and reference decreased across the break time.


        Perform 1x adjustment with the selected method of the class

        Parameters
        -------
        correct_below_0 : bool, optional (default: True)
            If there are values beyond the physical plausible range, these values
            are replaced with the minumum of the original input.
        adjust_separately : bool
            Adjust HSPa and all values before HSPa separately using the same model
            as found for HSPa.

        Returns
        -------
        df_adjust : pd.DataFrame
            The input and output values


        Checks if the adjustment raised an error or not.

        Parameters
        -------
        error_code_pass : list, optional (default : [0])
            List of error codes that dont lead to the checks to fail.

        Returns
        -------
        adjust_checks_pass : bool
            Indicates whether all checks passed or not.


        Write the linear model plot collection to image file.

        Parameters
        ----------
        save_path : str, optional (default: None)
            path and file name of the file that should be written.
        gpi : int, optional (default: None)
            Identifies the current collection for file name only.
            If this is None it's not included in the file name.


        Always plot the data, that is also adjusted.
        Plot time series and stats

        Parameters
        -------
        kind : str
            box or line
        save_path : str, optional
            Path where the image is stored
        title : str
            Title for the plot


        Always plot the data, that is also adjusted.
        Plot time series only

        Parameters
        -------
        save_path : str, optional
            Path where the image is stored
        title : str
            Title for the plot
        ax : matplotlib.axes.Axes
            Axes that is used for the plot

        Returns
        -------
        ax : matplotlib.axes.Axes
            Plot axes


    Resample a dataframe to the given temporal resolution ('M', 'D', etc.).
    If the number of valid values (not nans) in a resample period (eg. 'M')
    is smaller than the defined threshold, the resample will be NaN Parameters.
    ----------
    can_adj : pandas.Series
        DataFrame to resample
    how : str
        Time frame for temporal resampling, M = monthly, SMS= semi-month start, SM = semi-month end
        MM=month middle
    threshold : float
        % of valid observations (not nan) in period defined in 'how'
    Returns
    -------
    df_resampled : pd.Series
        The resampled Series

    df_count : pd.DataFrame
        Number of observations per period and threshold that had to be reached


    Wrapper around resample function to resample the input dataframe
    to the selected period, with the selected threshold for minimum
    temporal coverage in % per observation.

    Parameters
    -------
    ds_in : pandas.DataFrame
        DataFrame that should be resampled
    resample_to : 'str'
        Time period to resample to, eg M or D
    resample_threshold : float
        Minimum % of observations in the selected period to calculate a mean
        e.g. 0.1 = 10% valid observations, 1 = 100% valid observations

    Returns
    -------
    df_test_resampled : pd.DataFrame
        The resampled DataFrame


    Filters a data frame by dropping the >upper % and <lower % of all values.

    Parameters
    ----------
    df_in : pd.DataFrame
        Input dataframe, that is filtered
    filter_col : str
        Name of the column based on which the filtering is performed
    lower : float
        Lower threshold quantile
    upper :
        Upper threshold quantile

    Returns
    -------
    masked_values : pd.DataSeries
        Data Series of flags that show which values are outside the defined threshold


    Calculate the cross correlation between 2 pandas Series with the passed lag(s)

    Parameters
    ----------
    can : pd.Series
        Candidate data set (that is shifted)
    ref : pd.Series
        Reference data set (that is stationary)
    lag : int or list
        Lag(s) for which the correlations are calculated (can is shifted)
    method : str
        Correlation type, as in pd.corr ('pearson', 'spearman', etc.)

    Returns
    ----------
    ccorr : float or list
        Cross correlations between can and ref for the selected time lag(s)


    Calculate the auto correlation for a pandas Series with the passed lag(s)

    Parameters
    ----------
    can : pd.Series
        Candidate data set (that is shifted)
    lag : int or list
        Lag(s) for which the correlations are calculated
    method : str
        Correlation type, as in pd.corr ('pearson', 'spearman', etc.)

    Returns
    ----------
    acorr : float or list
        Auto correlations between can and ref for the selected time lag(s)


    Flattens a dict of dicts so that the keys of 2 levels are merged into 1 key which contains the data of the
    sublevel dictionary.

    Parameters
    ----------
    d : dict
        Dict of dicts that will be flattened.

    Returns
    -------
    flat : dict
        Flattened dictionary


    Find the
    Parameters
    ----------
    month : int or iterable
        month(s) to look up
    year : int or iterable
        year(s) of the passed month(s)
    astype : dtype, optional (default: int)
        int or float
    Returns
    -------
    days : np.array of float
        Days in the passed months


    Midmonth target values, that are objectively
    chosen so that the average of the daily adjustments over a given month is
    equal to the monthly adjustment, when performing linear interpolation.

    J. Sheng, F. Zwiers (1998)
    An improved scheme for time-dependent boundary conditions in atmospheric general circulation models
    https://link.springer.com/content/pdf/10.1007%2Fs003820050244.pdf

    LUCIE A. VINCENT AND X. ZHANG (2001)
    Homogenization of Daily Temperatures over Canada (2001)
    https://link.springer.com/article/10.1007/s003820050244

    Parameters
    ---------
    M : np.array
        Monthly values that are used to find the midmonth target values


    Detect the (highest) frequency in the passed date time index, and return it
    in a format the pandas can interpret.
    Also tries to detect whether the found freq is monthly or higher (slow)

    Parameters:
    -------
    dt : pd.DatetimeIndex
        The index that is explored

    Returns:
    --------
    unit : str
        Unit string of the used resolution
    ignore_M : bool
        Do not attempt to find out if the daily freq is monthly or lower (slow)


    Count the number of valid months instances (not nan) per month in the passed index,
    and how many there should be.

    Parameters
    ----------
    dt : pd.DatetimeIndex
        Valid indices (no nans) in monthly resolution
    first_should : datetime
        The first month that SHOULD have a value (may not be in dt if it is nan)
        Day in datetime is ignored
    last_should : datetime
        The first day that SHOULD have a value (may not be in dt if it is nan)
        Day in datetime is ignored

    Returns
    -------
    df_count: pd.DataFrame
        A data frame that contains the calculated statistics


    Count the number of days per month in the passed index, and how many there
    should be.

    Parameters
    ----------
    dt : pandas.DateTimeIndex
        Valid index in daily resolution
    first_should : datetime
        The first day that SHOULD have a value (may not be in dt if it is nan)
    last_should : datetime
        The first day that SHOULD have a value (may not be in dt if it is nan)

    Returns
    -------
    df_count: pd.DataFrame
        A data frame that contains the calculated statistics


    Compare the coverage of the first series to the second series.
    They are adjacent with the break time as the start of the second series and
    the end of the first series.

    Parameters
    ----------
    ds1 : pd.Series
        The data series before the break time
    ds2 : pd.Series
        The data series after the break time
    start : datetime
        The first date of the first set that COULD/SHOULD have a valid value
    end1 : datetime
        The last date of the first set that COULD/SHOULD have a valid
        observation
    end : datetime
        The last date of the second set that COULD/SHOULD have a valid value
    resolution : str
        D or M, which resolution the input is in
    coverdiff_max : float, between 0 and 1
        THe maximum difference for day/month that the coverage of the 2 groups
        may differ.

    Returns
    -------
    success : bool
        If the test succeeded or not, false means that months are to drop
    df_cover_1 : pd.DataFrame
        The coverage of days/months per month of the first input set
    df_cover_2 : pd.DataFrame
        The coverage of days/months per month of the second input set
    cover_diff : pd.DataFrame
        Differenes in temporal coverage of the 2 groups
    months_to_drop : np.array
        List of months that have to be removed from both sets (if they exist)


    Remove all values in the passed months in the dataframe

    Parameters
    ----------
    df : pandas.DataFrame or pandas.Series
        Time series data, that will be filtered
    drop_months : np.array
        List of integers for months that will be removed eg [1,2] for Jan and Feb

    Returns
    -------
    df_filtered : pandas.DataFrame or pandas.Series
        Input data frame without the selected months


        Resample the main data frame to the selected temporal resolution.
        Rescale then the reference column again.

        Returns
        -------
        df_adjust_resampled : pandas.DataFrame
            The resampled, re-scaled data frame.


        Returns titles for scatter plot first row visualizations, depending if
        the models are calculated from filtered or unfiltered, resampled or
        un-resampled data, and for which group.

        Parameters
        ----------
        group_no : int
            Group number (0 or 1) of group to create scatter plot title for

        Returns
        -------
        title : str
            Title for the plot with the current class configurations


        Model objects input data before/after break time via linear model.

        Parameters
        -------
        model_intercept : bool
            Set True to model slope and inter, False to model slope only
            (inter is then 0, and so is inter diff between the models)
        Returns
        -------
        model0 : LinearRegression
            The linear model for the FIRST part (before break)
        model1 : LinearRegression
            The linear model for the SECOND part (after break)


Specific for each child class