Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New user interface; major refactor of API and backend; docs and tests #11

Merged
merged 59 commits into from
Aug 27, 2024
Merged
Changes from 1 commit
Commits
Show all changes
59 commits
Select commit Hold shift + click to select a range
73fd3f5
model_wrapper now handles kwargs
harmsm Aug 6, 2024
4f71731
added VectorModelWrapper class to wrap models that take vector inputs
harmsm Aug 6, 2024
0a66a18
added ability to read parameter spreadsheet
harmsm Aug 7, 2024
6d93ac9
added ability to set modelwrapper parameters effeciently
harmsm Aug 8, 2024
e2d2b79
added openpyxl dependency
harmsm Aug 8, 2024
f7b00c2
full unit test coverage on model_wrapper, minor bug fixes
harmsm Aug 8, 2024
09a4a65
built user-facing wrap_model function
harmsm Aug 8, 2024
8a1b0a4
added ModelWrapper.dataframe property
harmsm Aug 8, 2024
50d59ad
added __repr__ to key classes
harmsm Aug 9, 2024
d8829e6
renamed BayesianFitter --> BayesianSampler
harmsm Aug 9, 2024
8b30152
removed 'name' attribute from FitParameter
harmsm Aug 9, 2024
d24852f
better default y_stdev setting, with warning
harmsm Aug 9, 2024
dfab76a
cleaned up Fitter.model setter, removed mw.values
harmsm Aug 9, 2024
8e53e81
minor code cleanup
harmsm Aug 9, 2024
e088d26
git fixed table rst in docstrings
harmsm Aug 9, 2024
6269c7d
intermediate commit; ModelWrapper now uses pandas
harmsm Aug 12, 2024
921c9fa
intermediate commit; VectorModelWrapper now working
harmsm Aug 12, 2024
e52bd0f
intermediate commit, model_wrapper/ submodule tests passing
harmsm Aug 12, 2024
e7a1b9c
intermediate commit; fitter almost working
harmsm Aug 13, 2024
8e47702
base fitter now passing all tests
harmsm Aug 13, 2024
416bcb3
full test coverage of fitters/base
harmsm Aug 13, 2024
7732414
MLFitter now has full test coverage
harmsm Aug 13, 2024
b9a408f
dataframe now processor now explicitly casts col to float
harmsm Aug 13, 2024
8bbc3f9
refactor on bayesian side; almost complete testing
harmsm Aug 14, 2024
1e55a68
new bayesian implementation almost fully tested
harmsm Aug 14, 2024
f7b227b
ml and bayesian now working and passing all tests
harmsm Aug 14, 2024
341f3be
nearly complete test coverage, all working
harmsm Aug 14, 2024
f988415
100% test coverage
harmsm Aug 14, 2024
062af69
updating docs and examples
harmsm Aug 15, 2024
fdef15e
Merge pull request #1 from harmsm/remove_FitParameter
harmsm Aug 15, 2024
b6454aa
Merge branch 'main' of github.com:harmsm/dataprob into remove_FitPara…
harmsm Aug 15, 2024
fc77912
updating docs
harmsm Aug 15, 2024
fbe8392
Merge branch 'remove_FitParameter'
harmsm Aug 15, 2024
b197b76
model_wrapper now sets non_fit_kwargs on initialization
harmsm Aug 16, 2024
cf01eb0
updated non_fit_parameters --> non_fit_kwargs
harmsm Aug 16, 2024
b4c87d7
model now passed into fitter directly
harmsm Aug 17, 2024
83ace3d
added plotting functionality
harmsm Aug 17, 2024
6179970
plotting suite complete
harmsm Aug 18, 2024
795bc92
small graphical styling change
harmsm Aug 18, 2024
c01190d
added publicly accessible non_fit_kwargs
harmsm Aug 19, 2024
307d4b5
removed too-clever mw.variable setter/getter
harmsm Aug 19, 2024
569b0d0
Fitter args to fit() rather than __init__
harmsm Aug 19, 2024
2edadc2
intermediate commit; refactor to util
harmsm Aug 19, 2024
61d7e45
removed y_obs and y_std setters
harmsm Aug 19, 2024
3e2ff85
fixing bad github workflow test
harmsm Aug 19, 2024
fa98c49
cleaning up tests
harmsm Aug 19, 2024
ea5dd49
removed an unnecessary abstraction layer in ModelWrapper
harmsm Aug 19, 2024
b8964b1
added dataprob.setup interface
harmsm Aug 19, 2024
dc9e641
docstring and import cleanup throughtout
harmsm Aug 19, 2024
c29a1af
adding integrated tests, fixing bugs they reveal
harmsm Aug 19, 2024
4230e56
more integrated tests, small api clean up revealed by tests
harmsm Aug 19, 2024
2839946
adding more integrated tests and matched notebook examples
harmsm Aug 20, 2024
55978d5
np.array(df["x"]) -> np.array(df["x"]).copy()
harmsm Aug 20, 2024
cfd7c7f
updating readme and docstrings
harmsm Aug 20, 2024
5e5595c
added docs and synced with code
harmsm Aug 27, 2024
b58621e
tweaked numerical tests; doc cleanup
harmsm Aug 27, 2024
8494211
tweaking uncertainty for better numerical stability on linear extrap
harmsm Aug 27, 2024
fed33e3
disabling flawed test
harmsm Aug 27, 2024
d355dda
added double numerical test
harmsm Aug 27, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
renamed BayesianFitter --> BayesianSampler
harmsm committed Aug 9, 2024
commit d8829e6bc35f98dcc14c054443ef2ce9ba46bb04
2 changes: 1 addition & 1 deletion src/dataprob/__init__.py
Original file line number Diff line number Diff line change
@@ -7,6 +7,6 @@

from .fitters.ml import MLFitter
from .fitters.bootstrap import BootstrapFitter
from .fitters.bayesian import BayesianFitter
from .fitters.bayesian import BayesianSampler


2 changes: 1 addition & 1 deletion src/dataprob/fitters/bayesian.py
Original file line number Diff line number Diff line change
@@ -247,7 +247,7 @@ def _find_uniform_value(bounds):
return np.log(finfo.resolution) - np.log((right - left))


class BayesianFitter(Fitter):
class BayesianSampler(Fitter):
"""
Use Bayesian MCMC to sample parameter space.
"""
56 changes: 28 additions & 28 deletions tests/dataprob/fitters/test_bayesian.py
Original file line number Diff line number Diff line change
@@ -5,7 +5,7 @@
import pandas as pd
from scipy import stats

from dataprob.fitters.bayesian import BayesianFitter
from dataprob.fitters.bayesian import BayesianSampler
from dataprob.fitters.bayesian import _find_normalization
from dataprob.fitters.bayesian import _reconcile_bounds_and_priors
from dataprob.fitters.bayesian import _find_uniform_value
@@ -210,15 +210,15 @@ def test__find_uniform_value():
assert np.isclose(value,expected_value)


def test_BayesianFitter__init__():
def test_BayesianSampler__init__():

# default args work. check to make sure super().__init__ actually ran.
f = BayesianFitter()
f = BayesianSampler()
assert f.fit_type == "bayesian"
assert f._num_obs is None

# args are being set
f = BayesianFitter(num_walkers=100,
f = BayesianSampler(num_walkers=100,
initial_walker_spread=1e-4,
ml_guess=True,
num_steps=100,
@@ -236,15 +236,15 @@ def test_BayesianFitter__init__():

# check num threads passing
with pytest.raises(NotImplementedError):
f = BayesianFitter(num_walkers=100,
f = BayesianSampler(num_walkers=100,
initial_walker_spread=1e-4,
ml_guess=True,
num_steps=100,
burn_in=0.1,
num_threads=0)

with pytest.raises(NotImplementedError):
f = BayesianFitter(num_walkers=100,
f = BayesianSampler(num_walkers=100,
initial_walker_spread=1e-4,
ml_guess=True,
num_steps=100,
@@ -253,22 +253,22 @@ def test_BayesianFitter__init__():

# Pass bad value into each kwarg to make sure checker is running
with pytest.raises(ValueError):
f = BayesianFitter(num_walkers=0)
f = BayesianSampler(num_walkers=0)
with pytest.raises(ValueError):
f = BayesianFitter(initial_walker_spread="stupid")
f = BayesianSampler(initial_walker_spread="stupid")
with pytest.raises(ValueError):
f = BayesianFitter(ml_guess="not a bool")
f = BayesianSampler(ml_guess="not a bool")
with pytest.raises(ValueError):
f = BayesianFitter(num_steps=1.2)
f = BayesianSampler(num_steps=1.2)
with pytest.raises(ValueError):
f = BayesianFitter(burn_in=0.0)
f = BayesianSampler(burn_in=0.0)
with pytest.raises(ValueError):
f = BayesianFitter(num_threads=-2)
f = BayesianSampler(num_threads=-2)

def test__setup_priors():

# basic functionality with a uniform and gaussian prior
f = BayesianFitter()
f = BayesianSampler()
assert not hasattr(f,"_prior_frozen_rv")
assert not hasattr(f,"_uniform_priors")
assert not hasattr(f,"_gauss_prior_means")
@@ -295,7 +295,7 @@ def test__setup_priors():
assert np.array_equal(f._gauss_prior_mask,[True,False])

# No gaussian priors
f = BayesianFitter()
f = BayesianSampler()
f.priors = np.array([[np.nan,np.nan],[np.nan,np.nan]])
f.bounds = np.array([[-np.inf,-np.inf],[np.inf,np.inf]])
f._setup_priors()
@@ -306,7 +306,7 @@ def test__setup_priors():
assert np.array_equal(f._gauss_prior_mask,[False,False])

# No uniform priors
f = BayesianFitter()
f = BayesianSampler()
f.priors = np.array([[1,2],[3,4]])
f.bounds = np.array([[-np.inf,-np.inf],[np.inf,np.inf]])
f._setup_priors()
@@ -319,7 +319,7 @@ def test__setup_priors():
assert np.array_equal(f._gauss_prior_mask,[True,True])

# check internal bounds calculation adjustment calculation
f = BayesianFitter()
f = BayesianSampler()
f.priors = np.array([[10],[5]])
f.bounds = np.array([[0],[20]])
f._setup_priors()
@@ -339,9 +339,9 @@ def test__setup_priors():
frozen_rv=stats.norm(loc=0,scale=1))
assert np.isclose(base_offset + bounds_offset,f._gauss_prior_offsets[0])

def test_BayesianFitter_ln_prior():
def test_BayesianSampler_ln_prior():

f = BayesianFitter()
f = BayesianSampler()
f.priors = np.array([[0],[1]])
f.bounds = np.array([[-1],[1]])
f._setup_priors()
@@ -369,7 +369,7 @@ def test_BayesianFitter_ln_prior():

# Now set up two priors, one gauss with one infinite bound, one uniform with
# infinte bound
f = BayesianFitter()
f = BayesianSampler()
f.priors = np.array([[2,np.nan],[10,np.nan]])
f.bounds = np.array([[-np.inf,-np.inf],[10,0]])
f._setup_priors()
@@ -395,16 +395,16 @@ def test_BayesianFitter_ln_prior():
value = f.ln_prior(np.array([-1,2]))
assert np.isclose(-np.inf,value)

def test_BayesianFitter__ln_prob(binding_curve_test_data):
def test_BayesianSampler__ln_prob(binding_curve_test_data):
pass


def test_BayesianFitter_ln_prob(binding_curve_test_data):
def test_BayesianSampler_ln_prob(binding_curve_test_data):
"""
Test calculation ,looking for proper error checking.
"""

f = BayesianFitter()
f = BayesianSampler()

input_params = binding_curve_test_data["input_params"]

@@ -437,13 +437,13 @@ def test_BayesianFitter_ln_prob(binding_curve_test_data):

L = f.ln_prob(input_params)

def xtest_BayesianFitter__fit():
def xtest_BayesianSampler__fit():
pass

def xtest_BayesianFitter__update_estimates():
def xtest_BayesianSampler__update_estimates():
pass

def xtest_BayesianFitter_fit_info():
def xtest_BayesianSampler_fit_info():
pass


@@ -458,7 +458,7 @@ def test_fit(binding_curve_test_data,fit_tolerance_fixture):

for model_key in ["generic_model","wrappable_model"]:

f = BayesianFitter()
f = BayesianSampler()
model = binding_curve_test_data[model_key]
guesses = binding_curve_test_data["guesses"]
df = binding_curve_test_data["df"]
@@ -521,7 +521,7 @@ def model_to_wrap(m=1,x=np.array([1,2,3])): return m*x
mw = ModelWrapper(model_to_fit=model_to_wrap)

# Run _fit_has_been_run, success branch
f = BayesianFitter()
f = BayesianSampler()
f.model = mw
f.fit(y_obs=np.array([2,4,6]))

@@ -535,7 +535,7 @@ def model_to_wrap(m=1,x=np.array([1,2,3])): return m*x
assert len(out) == 19

# Run not _fit_has_been_run
f = BayesianFitter()
f = BayesianSampler()
f.model = mw

out = f.__repr__().split("\n")