Beispiel #1
0
    def get_params(self, name, col=None):
        """Return model fit parameters for specified feature(s).

        Parameters
        ----------
        name : {'aperiodic_params', 'peak_params', 'gaussian_params', 'error', 'r_squared'}
            Name of the data field to extract across the group.
        col : {'CF', 'PW', 'BW', 'offset', 'knee', 'exponent'} or int, optional
            Column name / index to extract from selected data, if requested.
            Only used for name of {'aperiodic_params', 'peak_params', 'gaussian_params'}.

        Returns
        -------
        out : ndarray
            Requested data.

        Notes
        -----
        For further description of the data you can extract, check the FOOOFResults documentation.
        """

        if not self.group_results:
            raise RuntimeError('No model fit data is available to extract - can not proceed.')

        # If col specified as string, get mapping back to integer
        if isinstance(col, str):
            col = get_indices(self.aperiodic_mode)[col]

        # Pull out the requested data field from the group data
        # As a special case, peak_params are pulled out in a way that appends
        #  an extra column, indicating from which FOOOF run each peak comes from
        if name in ('peak_params', 'gaussian_params'):
            out = np.array([np.insert(getattr(data, name), 3, index, axis=1)
                            for index, data in enumerate(self.group_results)])
            # This updates index to grab selected column, and the last colum
            #  This last column is the 'index' column (FOOOF object source)
            if col is not None:
                col = [col, -1]
        else:
            out = np.array([getattr(data, name) for data in self.group_results])

        # Some data can end up as a list of separate arrays.
        #   If so, concatenate it all into one 2d array
        if isinstance(out[0], np.ndarray):
            out = np.concatenate([arr.reshape(1, len(arr)) \
                if arr.ndim == 1 else arr for arr in out], 0)

        # Select out a specific column, if requested
        if col is not None:
            out = out[:, col]

        return out
Beispiel #2
0
def update_sim_ap_params(sim_params, delta, field=None):
    """Update the aperiodic parameter definition in a SimParams object.

    Parameters
    ----------
    sim_params : SimParams
        Object storing the current parameter definition.
    delta : float or list of float
        Value(s) by which to update the parameters.
    field : {'offset', 'knee', 'exponent'} or list of string
        Field of the aperiodic parameter(s) to update.

    Returns
    -------
    new_sim_params : SimParams
        Updated object storing the new parameter definition.

    Raises
    ------
    InconsistentDataError
        If the input parameters and update values are inconsistent.
    """

    # Grab the aperiodic parameters that need updating
    ap_params = sim_params.aperiodic_params.copy()

    # If field isn't specified, check shapes line up and update across parameters
    if not field:
        if not len(ap_params) == len(delta):
            raise InconsistentDataError(
                "The number of items to update and "
                "number of new values is inconsistent.")
        ap_params = [param + update for param, update in zip(ap_params, delta)]

    # If labels are given, update deltas according to their labels
    else:
        # This loop checks & casts to list, to work for single or multiple passed in values
        for cur_field, cur_delta in zip(
                list([field]) if not isinstance(field, list) else field,
                list([delta]) if not isinstance(delta, list) else delta):
            data_ind = get_indices(infer_ap_func(ap_params))[cur_field]
            ap_params[data_ind] = ap_params[data_ind] + cur_delta

    # Replace parameters. Note that this copies a new object, as data objects are immutable
    new_sim_params = sim_params._replace(aperiodic_params=ap_params)

    return new_sim_params
Beispiel #3
0
    def get_params(self, name, col=None):
        """Return model fit parameters for specified feature(s).

        Parameters
        ----------
        name : {'aperiodic_params', 'peak_params', 'gaussian_params', 'error', 'r_squared'}
            Name of the data field to extract.
        col : {'CF', 'PW', 'BW', 'offset', 'knee', 'exponent'} or int, optional
            Column name / index to extract from selected data, if requested.
            Only used for name of {'aperiodic_params', 'peak_params', 'gaussian_params'}.

        Returns
        -------
        out : float or 1d array
            Requested data.

        Notes
        -----
        For further description of the data you can extract, check the FOOOFResults documentation.

        If there is no data on periodic features, this method will return NaN.
        """

        if self.aperiodic_params_ is None:
            raise RuntimeError(
                'No model fit data is available to extract - can not proceed.')

        # If col specified as string, get mapping back to integer
        if isinstance(col, str):
            col = get_indices(self.aperiodic_mode)[col]

        # Extract the request data field from object
        out = getattr(self, name + '_')

        # Periodic values can be empty arrays - if so replace with NaN array
        if isinstance(out, np.ndarray) and out.size == 0:
            out = np.array([np.nan, np.nan, np.nan])

        # Select out a specific column, if requested
        if col is not None:

            # Extract column, & if result is a single value in an array, unpack from array
            out = out[col] if out.ndim == 1 else out[:, col]
            out = out[0] if isinstance(out,
                                       np.ndarray) and out.size == 1 else out

        return out
Beispiel #4
0
def update_sim_ap_params(sim_params, delta, field=None):
    """Update the aperiodic parameter definition in a SimParams object.

    Parameters
    ----------
    sim_params : SimParams object
        Object storing the current parameter definitions.
    delta : float or list
        Value(s) by which to update the parameters.
    field : {'offset', 'knee', 'exponent'} or list of string
        Field of the aperiodic parameters to update.

    Returns
    -------
    new_sim_params : SimParams object
        Updated object storing the new parameter definitions.

    Notes
    -----
    SimParams is a `namedtuple`, which is immutable.
    Therefore, this function constructs and returns a new `SimParams` object.
    """

    ap_params = sim_params.aperiodic_params.copy()

    if not field:
        if not len(ap_params) == len(delta):
            raise ValueError('')
        ap_params = [ii + jj for ii, jj in zip(ap_params, delta)]

    else:
        field = list([field]) if not isinstance(field, list) else field
        delta = list([delta]) if not isinstance(delta, list) else delta

        for cur_field, cur_delta in zip(field, delta):
            dat_ind = get_indices(infer_ap_func(sim_params.aperiodic_params))[cur_field]
            ap_params[dat_ind] = ap_params[dat_ind] + cur_delta

    new_sim_params = SimParams(ap_params, *sim_params[1:])

    return new_sim_params
Beispiel #5
0
    def get_params(self, name, col=None):
        """Return model fit parameters for specified feature(s).

        Parameters
        ----------
        name : {'aperiodic_params', 'peak_params', 'gaussian_params', 'error', 'r_squared'}
            Name of the data field to extract across the group.
        col : {'CF', 'PW', 'BW', 'offset', 'knee', 'exponent'} or int, optional
            Column name / index to extract from selected data, if requested.
            Only used for name of {'aperiodic_params', 'peak_params', 'gaussian_params'}.

        Returns
        -------
        out : ndarray
            Requested data.

        Raises
        ------
        NoModelError
            If there are no model fit results available.
        ValueError
            If the input for the `col` input is not understood.

        Notes
        -----
        When extracting peak information ('peak_params' or 'gaussian_params'), an additional column
        is appended to the returned array, indicating the index of the model that the peak came from.
        """

        if not self.has_model:
            raise NoModelError(
                "No model fit results are available, can not proceed.")

        # Allow for shortcut alias, without adding `_params`
        if name in ['aperiodic', 'peak', 'gaussian']:
            name = name + '_params'

        # If col specified as string, get mapping back to integer
        if isinstance(col, str):
            col = get_indices(self.aperiodic_mode)[col]
        elif isinstance(col, int):
            if col not in [0, 1, 2]:
                raise ValueError("Input value for `col` not valid.")

        # Pull out the requested data field from the group data
        # As a special case, peak_params are pulled out in a way that appends
        #  an extra column, indicating which FOOOF run each peak comes from
        if name in ('peak_params', 'gaussian_params'):

            # Collect peak data, appending the index of the model it comes from
            out = np.vstack([
                np.insert(getattr(data, name), 3, index, axis=1)
                for index, data in enumerate(self.group_results)
            ])

            # This updates index to grab selected column, and the last column
            #  This last column is the 'index' column (FOOOF object source)
            if col is not None:
                col = [col, -1]
        else:
            out = np.array(
                [getattr(data, name) for data in self.group_results])

        # Select out a specific column, if requested
        if col is not None:
            out = out[:, col]

        return out