Python package for fitting a mean-field fitness-based two-star model (Fit2SM) for undirected binary networks (dcGM and UBCM are also available for comparisons).
Project description
fit2SM
fit2SM is a lightweight research package for reconstructing undirected binary networks from partial information.
In many economic and financial settings, the full adjacency matrix is unavailable, but node-level “fitness proxies”
(e.g., aggregate activity, volumes, exposures, total trading amounts) are observable and provide reliable information on
heterogeneity. fit2SM uses these proxies together with a small set of global constraints to build a faithful
probabilistic reconstruction of the network.
The package currently provides three solvers:
- dcGM (density-corrected Gravity Model): matches the expected number of links $L$ using strengths as fitness proxies.
- UBCM (Undirected Binary Configuration Model): matches the expected degrees $k_i$.
- Fit2SM (Fitness-based Two-Star Model, mean-field): matches $(L, S)$ where $S = \sum_i \binom{k_i}{2}$ is the total number of two-stars (wedges).
Why two-stars? Matching $S$ allows Fit2SM to reproduce the second moment of the degree distribution (and hence its variance), a key ingredient for processes whose behavior depends on both $\langle k \rangle$ and $\langle k^2 \rangle$ (e.g., epidemic thresholds, systemic-risk proxies, spectral indicators). See the accompanying paper for the model definition, motivation, and empirical validation:
- M. Marzi, F. Giuffrida, D. Garlaschelli, T. Squartini, Reproducing the first and second moment of empirical degree distributions, arXiv:2505.10373 (v2), DOI: 10.48550/arXiv.2505.10373.
Installation
The package is available on PyPI:
pip install fit2SM
For development:
git clone https://github.com/mattiamarzi/fit2SM
cd fit2SM
pip install -e ".[dev]"
pytest -q
Quick start (Fit2SM)
The Fit2SM solver takes as input:
- nonnegative fitness proxies
strengths, - the target number of links
L, - the target number of two-stars
S.
It returns the fitted parameters (z, y) and the reconstructed probability matrix $P=(p_{ij})$ (optionally).
import numpy as np
from fit2sm.fit2sm import Fit2SMModel
# Example inputs (replace with your own)
n = 200
rng = np.random.default_rng(0)
strengths = rng.lognormal(mean=0.0, sigma=1.0, size=n) # nonnegative fitness proxies
L_target = 1200.0 # expected number of links
S_target = 45000.0 # expected number of two-stars
model = Fit2SMModel(strengths=strengths, L=L_target, S=S_target)
# "Single-iteration" (fast) reconstruction: kappa is initialized from dcGM and not iterated further.
res = model.fit(outer_max_steps=1, inner_tol=1e-6, inner_max_iter=200, return_P=True)
print("z =", res.z)
print("y =", res.y)
print("L_hat =", res.L_hat, "target =", res.L_target)
print("S_hat =", res.S_hat, "target =", res.S_target)
P = res.P # fitted link probabilities
If you do not request return_P=True, you can still compute the probability matrix later:
P = model.probabilities()
If you have an observed adjacency matrix
If you do have a binary adjacency matrix $A$, you can compute targets as:
k_obs = A.sum(axis=1)
L_obs = 0.5 * A.sum()
S_obs = float(0.5 * np.sum(k_obs * (k_obs - 1.0)))
Advanced options (Fit2SM)
Outer self-consistency on $\kappa$
Fit2SM is defined in terms of hidden mean-field degrees $\kappa$. You can iterate them until self-consistency:
res = model.fit(
outer_max_steps=25,
outer_tol=1e-6,
inner_tol=1e-8,
)
Fixing $\kappa$ to a supplied degree sequence (like the observed one)
If you want to bypass the outer fixed point and keep $\kappa$ fixed, set use_true_degrees=True and pass degrees=...:
res = model.fit(
use_true_degrees=True,
degrees=k_obs,
)
Other solvers
You can also import and use dcGM and UBCM directly:
from fit2sm.dcgm import DcGMModel
from fit2sm.ubcm import UBCMModel
# dcGM (matches L using strengths)
dcgm = DcGMModel(strengths=strengths, L=L_target)
dcgm_res = dcgm.fit()
P_dcgm = dcgm_res.P
# UBCM (matches expected degrees)
ubcm = UBCMModel(degrees=k_obs)
ubcm_res = ubcm.fit()
P_ubcm = ubcm.probabilities()
Documentation
docs/usage.mddocs/api_quick_reference.mddocs/math.md
License
MIT, see LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file fit2sm-0.1.0.tar.gz.
File metadata
- Download URL: fit2sm-0.1.0.tar.gz
- Upload date:
- Size: 19.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
45f06efbee759c93a6d2ac9fcac9048f7d9a3249f7d5b3226cf4e2d82f9210ae
|
|
| MD5 |
ee36f46494997c8f8f1859c44a2f520e
|
|
| BLAKE2b-256 |
b1a69035006b0d15868448d335d1f0a86a0bc0907d419653b1734bc653875c3e
|
File details
Details for the file fit2sm-0.1.0-py3-none-any.whl.
File metadata
- Download URL: fit2sm-0.1.0-py3-none-any.whl
- Upload date:
- Size: 19.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f677a86ede7e0a32b6d1e77945a737d766c9cf78dc4638eb31bcecfb70bcc35d
|
|
| MD5 |
2a9595801bc980e592dd6bc89dbf6557
|
|
| BLAKE2b-256 |
c24e43fc7f30d6950f41bb742b2c5e1d043c743e32dd61818594526d3d93392b
|