aspire.samples
==============

.. py:module:: aspire.samples


Attributes
----------

.. autoapisummary::

   aspire.samples.logger


Classes
-------

.. autoapisummary::

   aspire.samples.BaseSamples
   aspire.samples.Samples
   aspire.samples.MCMCSamples
   aspire.samples.PTMCMCSamples
   aspire.samples.SMCSamples


Module Contents
---------------

.. py:data:: logger

.. py:class:: BaseSamples

   Class for storing samples and corresponding weights.

   If :code:`xp` is not specified, all inputs will be converted to match
   the array type of :code:`x`.


   .. py:attribute:: x
      :type:  array_api_compat.common._typing.Array

      Array of samples, shape (n_samples, n_dims).


   .. py:attribute:: log_likelihood
      :type:  array_api_compat.common._typing.Array | None
      :value: None


      Log-likelihood values for the samples.


   .. py:attribute:: log_prior
      :type:  array_api_compat.common._typing.Array | None
      :value: None


      Log-prior values for the samples.


   .. py:attribute:: log_q
      :type:  array_api_compat.common._typing.Array | None
      :value: None


      Log-probability values under the proposal distribution.


   .. py:attribute:: parameters
      :type:  list[str] | None
      :value: None


      List of parameter names.


   .. py:attribute:: dtype
      :type:  Any | str | None
      :value: None


      Data type of the samples.

      If None, the default dtype for the array namespace will be used.


   .. py:attribute:: xp
      :type:  Callable | None
      :value: None


      The array namespace to use for the samples.

      If None, the array namespace will be inferred from the type of :code:`x`.


   .. py:attribute:: device
      :type:  Any
      :value: None


      Device to store the samples on.

      If None, the device will be inferred from the array namespace of :code:`x`.


   .. py:property:: dims

      Number of dimensions (parameters) in the samples.


   .. py:method:: to_numpy(dtype = None)


   .. py:method:: to_namespace(xp, dtype = None)


   .. py:method:: array_to_namespace(x, dtype=None)

      Convert an array to the same namespace as the samples



   .. py:method:: to_dict(flat = True, copy = True)

      Convert the samples to a dictionary.

      :param flat: If True, the samples are stored as separate keys for each parameter.
                   If False, the samples are stored in a "samples" key as a dictionary
                   of parameter arrays.
      :type flat: :py:class:`bool`
      :param copy: If True, the arrays in the dictionary are deep-copied. If False, they
                   are not copied and may share memory with the original samples.
      :type copy: :py:class:`bool`

      :returns: A dictionary representation of the samples.
      :rtype: :py:class:`dict`



   .. py:method:: from_dict(dictionary)
      :classmethod:


      Load samples from a dictionary.

      The dictionary can either be in a flat format, where the samples are
      stored as separate keys for each parameter, or in a nested format, where
      the samples are stored in a "samples" key as a dictionary of parameter.



   .. py:method:: to_dataframe(include = None)

      Convert the samples to a pandas DataFrame.

      Only includes samples, log_likelihood, log_prior, and log_q by default,
      since additional fields have varying shapes and may not be compatible
      with a DataFrame format.

      :param include: List of fields to include in the DataFrame. If None, includes x,
                      log_likelihood, log_prior, and log_q. x is always included
                      irrespective of the value of include.
      :type include: :py:class:`list[str] | None`

      :returns: A DataFrame representation of the samples.
      :rtype: :py:class:`pd.DataFrame`



   .. py:method:: plot_corner(parameters = None, fig = None, **kwargs)

      Plot a corner plot of the samples.

      :param parameters: List of parameters to plot. If None, all parameters are plotted.
                         Figure to plot on. If None, a new figure is created.
      :type parameters: :py:class:`list[str] | None`
      :param \*\*kwargs: Additional keyword arguments to pass to corner.corner(). Kwargs
                         are deep-copied before use.
      :type \*\*kwargs: :py:class:`dict`



   .. py:method:: save(h5_file, path='samples', flat=False)

      Save the samples to an HDF5 file.

      This converts the samples to numpy and then to a dictionary.

      :param h5_file: The HDF5 file to save to.
      :type h5_file: :py:class:`h5py.File`
      :param path: The path in the HDF5 file to save to.
      :type path: :py:class:`str`
      :param flat: If True, save the samples as a flat dictionary.
                   If False, save the samples as a nested dictionary.
      :type flat: :py:class:`bool`



   .. py:method:: load(h5_file, path='samples')
      :classmethod:


      Load the samples from an HDF5 file.



   .. py:method:: concatenate(samples)
      :classmethod:


      Concatenate multiple Samples objects.



   .. py:method:: from_samples(samples, **kwargs)
      :classmethod:


      Create a Samples object from a BaseSamples object.



.. py:class:: Samples

   Bases: :py:obj:`BaseSamples`


   Class for storing samples and corresponding weights.

   If :code:`xp` is not specified, all inputs will be converted to match
   the array type of :code:`x`.


   .. py:attribute:: log_w
      :type:  array_api_compat.common._typing.Array


   .. py:attribute:: weights
      :type:  array_api_compat.common._typing.Array


   .. py:attribute:: evidence
      :type:  float


   .. py:attribute:: evidence_error
      :type:  float


   .. py:attribute:: log_evidence
      :type:  float | None
      :value: None



   .. py:attribute:: log_evidence_error
      :type:  float | None
      :value: None



   .. py:attribute:: effective_sample_size
      :type:  float


   .. py:property:: efficiency

      Efficiency of the weighted samples.

      Defined as ESS / number of samples.


   .. py:method:: compute_weights()

      Compute the posterior weights.



   .. py:property:: scaled_weights


   .. py:method:: rejection_sample(rng=None)


   .. py:method:: plot_corner(include_weights = True, **kwargs)

      Plot a corner plot of the samples.

      :param parameters: List of parameters to plot. If None, all parameters are plotted.
                         Figure to plot on. If None, a new figure is created.
      :type parameters: :py:class:`list[str] | None`
      :param \*\*kwargs: Additional keyword arguments to pass to corner.corner(). Kwargs
                         are deep-copied before use.
      :type \*\*kwargs: :py:class:`dict`



   .. py:method:: to_namespace(xp)


   .. py:method:: to_numpy()


   .. py:method:: to_dataframe(include = None)

      Convert the samples to a pandas DataFrame.

      By default, includes log_likelihood, log_prior, log_q, and log_w.
      See parent class for more details.

      :param include: List of fields to include in the DataFrame. If None, includes
                      log_likelihood, log_prior, log_q, and log_w.
      :type include: :py:class:`list[str] | None`

      :returns: A DataFrame representation of the samples.
      :rtype: :py:class:`pd.DataFrame`



.. py:class:: MCMCSamples

   Bases: :py:obj:`BaseSamples`


   Class for storing MCMC samples and chain metadata.

   Samples are stored flattened in :code:`x`, with :code:`chain_shape`
   capturing the original chain layout (excluding the parameter dimension).


   .. py:attribute:: chain_shape
      :type:  tuple[int, Ellipsis] | None
      :value: None


      Shape of the chain excluding the parameter dimension.


   .. py:attribute:: thin
      :type:  int | None
      :value: None


      Thinning factor used to produce the chain, if any.


   .. py:attribute:: burn_in
      :type:  int | None
      :value: None


      Number of burn-in steps removed, if any.


   .. py:attribute:: autocorrelation_time
      :type:  array_api_compat.common._typing.Array | None
      :value: None


      Autocorrelation time per dimension, if available.


   .. py:attribute:: minimum_chain_ndim
      :type:  ClassVar[int]
      :value: 2


      Minimum required dimensionality for the input chain.


   .. py:method:: from_chain(chain, log_likelihood=None, log_prior=None, log_q=None, parameters=None, xp=None, dtype = None, device = None, thin = None, burn_in = None, autocorrelation_time = None, **extra_kwargs)
      :classmethod:


      Create samples from a chain array.

      :param chain: MCMC chain with shape (..., n_dims). For a single chain, this
                    is typically (n_steps, n_dims). For ensemble samplers, use
                    (n_steps, n_walkers, n_dims).
      :param log_likelihood: Optional arrays matching the chain shape without the last
                             dimension. They will be flattened to align with :code:`x`.
      :param log_prior: Optional arrays matching the chain shape without the last
                        dimension. They will be flattened to align with :code:`x`.
      :param log_q: Optional arrays matching the chain shape without the last
                    dimension. They will be flattened to align with :code:`x`.
      :param parameters: Optional list of parameter names.
      :param xp: Optional array namespace. If None, inferred from :code:`chain`.
      :param dtype: Optional dtype to use for stored arrays.
      :param device: Optional device to place arrays on.
      :param thin: Optional metadata describing how the chain was processed.
      :param burn_in: Optional metadata describing how the chain was processed.



   .. py:property:: chain

      The chain reshaped to its original layout


   .. py:property:: n_steps
      :type: int


      Number of steps in the chain, excluding walkers


   .. py:property:: n_chains
      :type: int


      Number of parallel chains (e.g. walkers), if applicable.


   .. py:method:: post_process(burn_in = 0, thin = 1)

      Return a new MCMCSamples object with burn-in discarded and/or thinned.



   .. py:method:: to_numpy()


.. py:class:: PTMCMCSamples

   Bases: :py:obj:`MCMCSamples`


   Class for storing parallel-tempered MCMC samples.


   .. py:attribute:: betas
      :type:  array_api_compat.common._typing.Array | None
      :value: None


      Inverse temperatures for the chains.

      Should be a 1D array of shape (n_temps,) in decreasing order, starting at 1.


   .. py:attribute:: minimum_chain_ndim
      :type:  ClassVar[int]
      :value: 3


      Minimum required dimensionality for the PTMCMC input chain.


   .. py:method:: subsample(n_samples_per_temperature, rng=None)

      Subsample the chain to a fixed number of samples per temperature.

      Samples are drawn without replacement independently for each temperature.

      :param n_samples_per_temperature: Number of samples to draw per temperature.
      :param rng: Optional numpy random generator. If None, a new one is created.



   .. py:method:: from_chain(chain, betas=None, log_likelihood=None, log_prior=None, log_q=None, parameters=None, xp=None, dtype = None, device = None, thin = None, burn_in = None, autocorrelation_time = None)
      :classmethod:


      Create samples from a parallel-tempered MCMC chain.

      :param chain: PTMCMC chain with shape (n_temps, ..., n_dims). A common layout
                    is (n_temps, n_steps, n_walkers, n_dims).
      :param betas: Optional inverse temperatures with shape (n_temps,).
      :param log_likelihood: Optional arrays matching the chain shape without the last
                             dimension. They will be flattened to align with :code:`x`.
      :param log_prior: Optional arrays matching the chain shape without the last
                        dimension. They will be flattened to align with :code:`x`.
      :param log_q: Optional arrays matching the chain shape without the last
                    dimension. They will be flattened to align with :code:`x`.
      :param parameters: Optional list of parameter names.
      :param xp: Optional array namespace. If None, inferred from :code:`chain`.
      :param dtype: Optional dtype to use for stored arrays.
      :param device: Optional device to place arrays on.
      :param thin: Optional metadata describing how the chain was processed.
      :param burn_in: Optional metadata describing how the chain was processed.



   .. py:property:: n_temps
      :type: int


      Number of temperatures in the parallel-tempered chain.


   .. py:method:: at_temperature(index)


   .. py:method:: cold_chain()


   .. py:method:: log_evidence_thermodynamic_integration(burn_in_fraction = 0.1, method = 'variance')

      Compute the log evidence using thermodynamic integration.

      .. rubric:: Notes

      By default, follows the implementation outlined in Section 2.1.3 of
      Annis et al. (2019) [1]_. If method="variance", the error is estimated
      using the variance of the TI estimate across samples as in Eq. (37).
      If method="coarse", the error is estimated by comparing to a coarser
      integration using every other temperature, as in the original ptemcee
      implementation.

      .. [1] Annis, J., et al. https://doi.org/10.1016/j.jmp.2019.01.005

      :param burn_in_fraction: Fraction of initial samples to discard as burn-in. If None, no burn-in is discarded.
                               This is applied independently to each temperature chain before integration.
      :param method: Method for estimating the uncertainty in the log evidence.
                     Options are "variance" or "coarse". See Notes for details.

      :returns: * :py:class:`log_evidence` -- The estimated log evidence from thermodynamic integration.
                * :py:class:`log_evidence_error` -- An estimate of the uncertainty in the log evidence.



   .. py:method:: log_evidence_stepping_stone(burn_in_fraction = 0.1)

      Compute the log evidence using the stepping-stone estimator.

      .. rubric:: Notes

      Follows the implementation outlined in Section 2.2.3 of Annis et al. (2019) [1]_

      .. [1] Annis, J., et al. https://doi.org/10.1016/j.jmp.2019.01.005

      :param burn_in_fraction: Fraction of initial samples to discard as burn-in. If None, no burn-in is discarded.
                               This is applied independently to each temperature chain before integration.

      :returns: * :py:class:`log_evidence` -- The estimated log evidence from thermodynamic integration.
                * :py:class:`log_evidence_error` -- An estimate of the uncertainty in the log evidence.



   .. py:method:: plot_chain(beta_index, n_walkers = None, burn_in = 0, parameters = None, fig = None, **kwargs)


.. py:class:: SMCSamples

   Bases: :py:obj:`BaseSamples`


   Class for storing samples and corresponding weights.

   If :code:`xp` is not specified, all inputs will be converted to match
   the array type of :code:`x`.


   .. py:attribute:: beta
      :type:  float | None
      :value: None


      Temperature parameter for the current samples.


   .. py:attribute:: log_evidence
      :type:  float | None
      :value: None


      Log evidence estimate for the current samples.


   .. py:attribute:: log_evidence_error
      :type:  float | None
      :value: None


      Log evidence error estimate for the current samples.


   .. py:method:: log_p_t(beta)


   .. py:method:: unnormalized_log_weights(beta)


   .. py:method:: log_evidence_ratio(beta)


   .. py:method:: log_evidence_ratio_variance(beta)

      Estimate the variance of the log evidence ratio using the delta method.

      Defined as Var(log Z) = Var(w) / (E[w])^2 where w are the unnormalized weights.



   .. py:method:: log_weights(beta)


   .. py:method:: resample(beta, n_samples = None, rng = None)

      Resample the samples to a new inverse temperature beta.

      If :code:`beta` is the same as the current beta and :code:`n_samples`
      is None or equal to the current number of samples, returns the same
      samples with updated beta.



   .. py:method:: to_standard_samples()

      Convert the samples to standard samples.



   .. py:method:: to_numpy()


