Metadata-Version: 2.4
Name: pelycan
Version: 0.2.0
Summary: PEculiar veLocitY for Cosmological ANalysis: A modular Python toolkit to model, analyze, and compare pairwise velocities and dispersions.
Author-email: Mariana Jaber <mariana.jaber@ncbj.gov.pl>, Antonela Taverna <maria.taverna@ncbj.gov.pl>, Rasmus Strid <rasmus.strid@ncbj.gov.pl>
License-Expression: MIT
Project-URL: Homepage, https://github.com/PAIRSteam/pelycan
Project-URL: Repository, https://github.com/PAIRSteam/pelycan
Project-URL: Issues, https://github.com/PAIRSteam/pelycan/issues
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Science/Research
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Operating System :: OS Independent
Classifier: Topic :: Scientific/Engineering :: Astronomy
Classifier: Topic :: Scientific/Engineering :: Physics
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: numpy
Requires-Dist: scipy>=1.7
Requires-Dist: camb
Requires-Dist: astropy
Requires-Dist: pandas
Requires-Dist: matplotlib
Provides-Extra: inference
Requires-Dist: cobaya; extra == "inference"
Requires-Dist: mpi4py>=3.0.0; extra == "inference"
Requires-Dist: getdist; extra == "inference"
Provides-Extra: test
Requires-Dist: pytest; extra == "test"
Requires-Dist: pytest-mock; extra == "test"
Requires-Dist: pytest-cov; extra == "test"
Provides-Extra: docs
Requires-Dist: sphinx; extra == "docs"
Requires-Dist: sphinx-rtd-theme; extra == "docs"
Requires-Dist: myst-parser; extra == "docs"
Provides-Extra: lint
Requires-Dist: ruff<0.17,>=0.16; extra == "lint"
Dynamic: license-file

# PELYCAN

### **PE**culiar ve**L**ocit**Y** for **C**osmological **AN**alysis

![logo](https://raw.githubusercontent.com/PAIRSteam/pelycan/main/assets/pelycan_logo.png)

**A modular Python toolkit to model, analyze, and compare pairwise velocities and dispersions.**

Developed by the [PAIRS team][pairs-team] [![GitHub](https://img.shields.io/badge/-GitHub-181717?style=flat&logo=github)][pairs-github]

[![CI](https://github.com/PAIRSteam/pelycan/actions/workflows/ci.yml/badge.svg)][ci-badge]
[![PyPI](https://img.shields.io/pypi/v/pelycan.svg)][pypi-badge]
[![Python versions](https://img.shields.io/pypi/pyversions/pelycan.svg)][pypi-badge]
[![Docs](https://readthedocs.org/projects/pelycan/badge/?version=latest)][docs-badge]

## Overview

The current release (v0.2.0) implements the theoretical model:

  - Input: cosmological parameters + redshift

  - Output: mean pairwise velocity v₁₂(r,a)

  The physics chain, implemented in pelycan/model/ (using pelycan/cosmology/ for
  background quantities):
  CAMB → P(k) → ξ(r) → ξ̄(r) → ∂ξ̄/∂a → v₁₂(r) = −H(a)·a²·r·∂ξ̄/∂a / [3·(1+ξ)]

  Comparing v₁₂(r) to simulation measurements via a Gaussian likelihood and sampling the
  parameters with Cobaya (`pelycan/inference/`) is available since v0.2.0; see
  [Sampling](#sampling-inference).
  

## Features

**Available now (v0.2.0):**
- Predict mean pairwise velocity $v_{12}(r,a)$ for a given cosmology (dispersion coming soon!)
- Compare theoretical predictions to simulations with a Gaussian likelihood, with
  optional Hartlap or Sellentin-Heavens corrections for a covariance estimated from mocks
- Run parameter inference (h, Ωc h², lnAₛ, ...) using [Cobaya](https://cobaya.readthedocs.io/en/latest/index.html)



## Project Structure

```text
pelycan/
|
├─ pelycan/
│  ├─ model            # v12(r) theory pipeline: P(k) -> xi(r) -> v12
│  ├─ cosmology        # Cosmology/background utilities (H(a), a<->z, load_cosmology)
│  └─ inference        # Cobaya likelihood + MCMC entry points
|
├─ main/
│  ├─ run_pelycan.py   # Quickstart script to run the model
│  └─ tutorial.ipynb   # Full walkthrough notebook
|
├─ tests/              # Unit tests (camb/, cosmology/, unit/)
|
└─ data/               # Post-processed data containing v12, sigma12 and errors
```



## Installation

By default, only the core dependencies for the v₁₂(r) model (`numpy`, `scipy`, `camb`,
`astropy`, `pandas`, `matplotlib`) are installed. The inference stack (`cobaya`,
`mpi4py`, `getdist`) is an optional extra, since `mpi4py` requires a system
MPI install and isn't needed to just run the model.

### From PyPI (recommended)
```bash
pip install pelycan
```
To also pull in the inference dependencies:
```bash
pip install pelycan[inference]
```

### Standard installation from source:
Clone the repository and install with pip:

```bash
git clone https://github.com/PAIRSteam/pelycan.git
cd pelycan
pip install .
# or, with the inference extras:
pip install .[inference]
```
### Development installation
To modify or contribute to the code, install in editable mode:
```bash
git clone https://github.com/PAIRSteam/pelycan.git
cd pelycan
pip install -e .[test]
```



## Running the Code

Quickstart: run the model for one cosmology/redshift and plot v₁₂(r), no simulation
data needed (run from the repo root):

```bash
python main/run_pelycan.py
```

For a full walkthrough (loading simulation data, comparing linear vs. non-linear vs.
quasi-linear variants), see [`main/tutorial.ipynb`](main/tutorial.ipynb).

### Sampling (inference)

Needs the inference extra (`pip install pelycan[inference]`, see [Installation](#installation)).
This short chain (about 2 minutes) fits `Ωc h²` to the Quijote v₁₂(r) at z=0.5 (run from the repo root):

```python
import numpy as np
from pelycan.cosmology.cosmology import load_cosmology
from pelycan.inference import cobaya_sampler

base = "v12_log_0.1_140.0_40_quijote_midres_dm_z05_10per_seed123_realiz_N100"
data = np.loadtxt(f"data/quijote/{base}_median.txt")   # columns: r, v12, err_min_max, sig_cov
covmat = np.loadtxt(f"data/quijote/CovMat_{base}.txt")

info, sampler, seconds = cobaya_sampler(
    param_settings={"omch2": None},        # None: default prior, reference and proposal
    cosmo_ll=load_cosmology.Quijote(),     # fixed parameters and fiducial values
    prefix="quickstart",
    redshifts_simulation=[0.0, 0.5],
    z_eval=0.5,
    r_data=data[:, 0], v12_sim=data[:, 1], v12_err=covmat,
    path_to_chains="chains/",
    nsteps=20,                             # accepted samples: just to check that it runs
    compute_derived=False,                 # skip the extra CAMB calls per step
    model_kwargs={"use_no_h_units": False},  # r_data is in Mpc/h; True if it is in Mpc
    mcmc_kwargs={"Rminus1_stop": 0.1},     # loose convergence, for a quick run
)
```

`model_kwargs` must include `use_no_h_units` (see **Units** below); the other model
options (`z_model`, `halofit`, `backend`, ...) are optional and go in the same
dict, alongside the Cobaya `mcmc` sampler options in `mcmc_kwargs`; see the docstrings of
`cobaya_sampler` and `make_config_dict`. For a complete example, see
[`main/demo_cobaya_sampler.py`](main/demo_cobaya_sampler.py). Plot helpers are in
`pelycan.inference.plots`.

> **Units:** `use_no_h_units` has no default and must be set explicitly: `False` if
> `r_data`/`rmin`/`rmax` are in Mpc/h, `True` if they are in Mpc. Omitting it raises
> `ValueError` when the likelihood is built (it used to silently default to `False`,
> which gives a badly wrong likelihood for data actually in Mpc). Since this can only
> check that the key is set, not that its value actually matches your data's units, a
> warning restating the units contract is also raised every time -- double-check it
> matches `r_data` before trusting the result.

## Tests

```bash
pip install -e .[test]
pytest tests/
```

To skip the slower tests (real CAMB calls, or heavy `pk2xi` numerical quadrature):

```bash
pytest tests/ -m "not slow"
```

To check test coverage:

```bash
pytest --cov=pelycan --cov-report=term-missing tests/
```

##  Contributing

Please:

* Use feature branches for development
* Write clear commit messages and PRs
* Lint the package before opening a PR (the CI runs the same check):
  ```bash
  pip install -e .[lint]
  ruff check pelycan
  ```
* Open issues for bugs, questions, or ideas

## Citation

If you use this code, please cite the papers:

* Jaber M., Taverna A., Strid R., Hellwing W.~A., 2026, arXiv:2609.07976. Submitted to PhRvD.
* Jaber M., Hellwing W.~A., Garcia-Farieta J.~E., Gupta S., Bilicki M., 2024, PhRvD, 109, 123528. doi:10.1103/PhysRevD.109.123528

## Authors

* Mariana Jaber, [Github mjaber](https://github.com/MarianaJBr), [INSPIRE Profile][inspire-mjaber]
* Antonela Taverna, [Github antotaverna](https://github.com/antotaverna), [ORCID Profile][orcid-antotaverna]
* Rasmus Strid, [Github R-Strid](https://github.com/R-Strid)


<!-- Links -->

[pairs-team]: https://marianajbr.github.io/pairs/index.html

[pairs-github]: https://github.com/PAIRSteam

[ci-badge]: https://github.com/PAIRSteam/pelycan/actions/workflows/ci.yml

[pypi-badge]: https://pypi.org/project/pelycan/

[docs-badge]: https://pelycan.readthedocs.io/en/latest/

[miniconda-site]: https://docs.conda.io/en/latest/miniconda.html

[conda-guide]: https://docs.conda.io/projects/conda/en/latest/user-guide/index.html

[poetry-url]: https://python-poetry.org/

[pypi-url]: https://pypi.org/

[conda-forge-url]: https://conda-forge.org/

[repo-url]: https://github.com/oarodriguez/cosmostat

[cobayay-url]: https://cobaya.readthedocs.io/en/latest/index.html

[gh-mjaber]: https://github.com/MarianaJBr

[inspire-mjaber]: https://inspirehep.net/authors/1707914

[gh-antotaverna]: https://github.com/antotaverna

[orcid-antotaverna]: https://orcid.org/0000-0003-1864-005X


