|
| 1 | +|release v0.7.0|_ |
| 2 | +================= |
| 3 | + |
| 4 | +This is a minor release from ``v0.6.3`` → ``v0.7.0``. |
| 5 | + |
| 6 | +Important Notes |
| 7 | +--------------- |
| 8 | + |
| 9 | +* Please note this release has **API breaking changes** and carefully read these |
| 10 | + notes while updating your code to the ``v0.7.0`` API. |
| 11 | +* All backends are now fully compatible and tested with |
| 12 | + `Python 3.10 <https://peps.python.org/pep-0310/>`_. |
| 13 | + (PR :pr:`1809`) |
| 14 | +* The ``pyhf.tensorlib.poisson`` API now allows for the expected rate parameter |
| 15 | + ``lam`` to be ``0`` in the case that the observed events ``n`` is ``0`` given |
| 16 | + that the limit :math:`\lim_{\lambda \to 0} \,\mathrm{Pois}(n | \lambda)` is well defined. |
| 17 | + (PR :pr:`1657`) |
| 18 | +* :func:`pyhf.readxml.parse` now supports reading of XML configurations with absolute paths. |
| 19 | + To support this, ``pyhf xlm2json`` now has a ``-v/--mount`` option. |
| 20 | + (PR :pr:`1909`) |
| 21 | +* Support for model specifications without a parameter of interest defined is added. |
| 22 | + (PRs :pr:`1638`, :pr:`1636`) |
| 23 | +* The :class:`pyhf.parameters.paramsets` classes ``suggested_fixed`` attribute behavior has |
| 24 | + been updated. |
| 25 | + To access the behavior used in ``pyhf`` ``v0.6.x`` use the ``suggested_fixed_as_bool`` attribute. |
| 26 | + (PR :pr:`1639`) |
| 27 | +* ``pyhf.pdf._ModelConfig.par_names`` is changed to be a property attribute. |
| 28 | + (PR :pr:`2027`) |
| 29 | +* The order of model parameters is now sorted by model parameter name. |
| 30 | + (PR :pr:`1625`) |
| 31 | +* Support for writing user custom modifiers is added. |
| 32 | + (PRs :pr:`1625`, :pr:`1644`) |
| 33 | +* Performance in :class:`pyhf.readxml` is increased by improvements to |
| 34 | + :func:`pyhf.readxml.import_root_histogram`. |
| 35 | + (PR :pr:`1691`) |
| 36 | +* :func:`pyhf.contrib.utils.download` is now more robust to different target file types. |
| 37 | + (PRs :pr:`1697`, :pr:`1704`) |
| 38 | +* A ``pyhf.default_backend`` has been added that is configurable through a |
| 39 | + ``default`` kwarg in :func:`pyhf.set_backend`. |
| 40 | + (PR :pr:`1646`) |
| 41 | + This is part of work to make ``pyhf`` fully automatic differentiable. |
| 42 | + (Issue :issue:`882`) |
| 43 | +* Schema validation now allows for both :class:`list` and ``pyhf.tensorlib`` objects |
| 44 | + to exist in the model specification. |
| 45 | + (PR :pr:`1647`) |
| 46 | +* The minimum required dependencies have been updated to support added features: |
| 47 | + |
| 48 | + - ``scipy>=1.2.0`` (PR :pr:`1274`) |
| 49 | + - ``click>=8.0.0`` (PRs :pr:`1909`, :pr:`1958`) |
| 50 | + - ``jsonschema>=4.15.0`` (PRs :pr:`1976`, :pr:`1979`) |
| 51 | + - ``importlib_resources>=1.4.0`` (for Python 3.7, 3.8) (PR :pr:`1979`) |
| 52 | + - ``typing_extensions>=3.7.4.3`` (for Python 3.7 only) (PRs :pr:`1940`, :pr:`1961`) |
| 53 | + |
| 54 | +* The minimum required backend versions have been updated to support added features: |
| 55 | + |
| 56 | + - JAX backend requires ``jax>=0.2.10``, ``jaxlib>=0.1.61`` (PR :pr:`1962`) |
| 57 | + - PyTorch backend requires ``torch>=1.10.0`` (PR :pr:`1657`) |
| 58 | + - TensorFlow backend requires ``tensorflow>=2.7.0``, ``tensorflow-probability>=0.11.0`` (PRs :pr:`1962`, :pr:`1657`) |
| 59 | + - iminuit optimizer requires ``iminuit>=2.7.0`` (PR :pr:`1895`) |
| 60 | + - ``'xmlio'`` extra requires ``uproot>=4.1.1`` (PR :pr:`1567`) |
| 61 | + |
| 62 | +Fixes |
| 63 | +----- |
| 64 | + |
| 65 | +* Use improvements to ``jsonschema.RefResolver`` to avoid |
| 66 | + ``jsonschema.exceptions.RefResolutionError``. |
| 67 | + (PR :pr:`1976`) |
| 68 | + |
| 69 | +* Use the conditional maximum likelihood estimators of the nuisance parameters |
| 70 | + to create the sampling distributions for :class:`pyhf.infer.calculators.ToyCalculator`. |
| 71 | + (PR :pr:`1610`) |
| 72 | + This follows the joint recommendations of the ATLAS and CMS experiments in |
| 73 | + |LHC Higgs search combination procedure|_. |
| 74 | + |
| 75 | +Features |
| 76 | +-------- |
| 77 | + |
| 78 | +Python API |
| 79 | +~~~~~~~~~~ |
| 80 | + |
| 81 | +* The following functions have been added to the ``pyhf.tensorlib`` API: |
| 82 | + |
| 83 | + |
| 84 | + - ``pyhf.tensorlib.transpose`` (PR :pr:`1696`) |
| 85 | + - ``pyhf.tensorlib.percentile`` (PR :pr:`817`) |
| 86 | + |
| 87 | +* :func:`pyhf.readxml.parse` now supports reading of XML configurations with absolute paths |
| 88 | + with the addition of the ``mounts`` optional argument. |
| 89 | + (PR :pr:`1909`) |
| 90 | + |
| 91 | +* Support for overriding the paths for finding schemas is added, using the ``pyhf`` |
| 92 | + installed location as a base via ``pyhf.utils.schemas``. |
| 93 | + (PRs :pr:`1753`, :pr:`1818`) |
| 94 | + |
| 95 | + .. code:: pycon |
| 96 | +
|
| 97 | + >>> from pathlib import Path |
| 98 | + >>> import pyhf.schema |
| 99 | + >>> current_schema_path = pyhf.schema.path |
| 100 | + >>> current_schema_path |
| 101 | + PosixPath('/path/to/your/venv/lib/python3.X/site-packages/pyhf/schemas') |
| 102 | + >>> custom_schema_path = Path("/path/to/custom/pyhf/schema") |
| 103 | + >>> with pyhf.schema(custom_schema_path): |
| 104 | + ... print(repr(pyhf.schema.path)) |
| 105 | + ... |
| 106 | + PosixPath('/path/to/custom/pyhf/schema') |
| 107 | + >>> pyhf.schema.path |
| 108 | + PosixPath('/path/to/your/venv/lib/python3.X/site-packages/pyhf/schemas') |
| 109 | +
|
| 110 | +* In :func:`pyhf.workspace.Workspace.model` the parameter of interest specified |
| 111 | + in the measurement may now be overridden using the added ``poi_name`` kwarg. |
| 112 | + (PR :pr:`1636`) |
| 113 | + |
| 114 | +* The :class:`pyhf.parameters.paramsets` classes ``suggested_fixed`` attribute behavior has |
| 115 | + been updated to return a :class:`list` of :class:`bool` of length ``n_parameters``. |
| 116 | + To access the behavior used in ``pyhf`` ``v0.6.x`` use the ``suggested_fixed_as_bool`` attribute. |
| 117 | + (PR :pr:`1639`) |
| 118 | + |
| 119 | +* ``pyhf.pdf._ModelConfig.par_names`` is changed to be a property attribute. |
| 120 | + (PR :pr:`2027`) |
| 121 | + |
| 122 | +* The order of model parameters is now sorted by model parameter name. |
| 123 | + (PR :pr:`1625`) |
| 124 | + |
| 125 | + .. code:: pycon |
| 126 | +
|
| 127 | + >>> import pyhf |
| 128 | + >>> model = pyhf.simplemodels.correlated_background( |
| 129 | + ... signal=[12.0, 11.0], |
| 130 | + ... bkg=[50.0, 52.0], |
| 131 | + ... bkg_up=[45.0, 57.0], |
| 132 | + ... bkg_down=[55.0, 47.0], |
| 133 | + ... ) |
| 134 | + >>> model.config.par_order |
| 135 | + ['correlated_bkg_uncertainty', 'mu'] |
| 136 | + >>> model.config.par_names |
| 137 | + ['correlated_bkg_uncertainty', 'mu'] |
| 138 | +
|
| 139 | +* Support for writing user custom modifiers is added. |
| 140 | + (PRs :pr:`1625`, :pr:`1644`) |
| 141 | + This is still in the stage where it is `targeted at expert users |
| 142 | + <https://github.com/scikit-hep/pyhf/issues/850#issuecomment-1239975121>`_. |
| 143 | + |
| 144 | +* ``{modifier}_builder`` classes are added for all modifiers. |
| 145 | + (PRs :pr:`1625`) |
| 146 | + For example, :class:`pyhf.modifiers.histosys.histosys_builder`. |
| 147 | + |
| 148 | +* When using ``pyhf.writexml`` and the ``normfactor`` parameter config is missing |
| 149 | + ``inits`` or ``bounds``, fall back to using default values. |
| 150 | + (PRs :pr:`1819`) |
| 151 | + |
| 152 | +* Supported options for :func:`pyhf.infer.hypotest` can now be passed as kwargs |
| 153 | + through the :func:`pyhf.infer.intervals.upper_limits.upper_limit` API. |
| 154 | + (PR :pr:`1613`) |
| 155 | + This now enables things like using :class:`pyhf.infer.calculators.ToyCalculator` |
| 156 | + as the calculator used for the hypothesis test scan: |
| 157 | + |
| 158 | + .. code:: pycon |
| 159 | +
|
| 160 | + >>> import numpy as np |
| 161 | + >>> import pyhf |
| 162 | + >>> pyhf.set_backend("jax") |
| 163 | + >>> model = pyhf.simplemodels.uncorrelated_background( |
| 164 | + ... signal=[12.0, 11.0], bkg=[50.0, 52.0], bkg_uncertainty=[3.0, 7.0] |
| 165 | + ... ) |
| 166 | + >>> observations = [51, 48] |
| 167 | + >>> data = pyhf.tensorlib.astensor(observations + model.config.auxdata) |
| 168 | + >>> scan = np.linspace(0, 5, 21) |
| 169 | + >>> obs_limit, exp_limits, (scan, results) = pyhf.infer.intervals.upper_limits.upper_limit( |
| 170 | + ... data, model, scan, return_results=True, calctype="toybased", ntoys=3000 |
| 171 | + ... ) |
| 172 | +
|
| 173 | +* Allow for fit parameter values from required fits in ``pyhf.infer.test_statistics`` |
| 174 | + functions to be returned by use of ``return_fitted_pars`` kwarg with the |
| 175 | + ``pyhf.infer.test_statistics`` functions and ``return_calculator`` kwarg with |
| 176 | + :func:`pyhf.infer.hypotest`. |
| 177 | + (PR :pr:`1554`) |
| 178 | + |
| 179 | +* A ``validate`` kwarg has been added to :func:`pyhf.workspace.Workspace` and |
| 180 | + :func:`pyhf.pdf.Model` to allow skipping validation. |
| 181 | + (PR :pr:`1646`) |
| 182 | + This should only be used by expert users who understand the risks. |
| 183 | + |
| 184 | +* A ``pyhf.default_backend`` has been added that is configurable through a |
| 185 | + ``default`` kwarg in :func:`pyhf.set_backend`. |
| 186 | + (PR :pr:`1646`) |
| 187 | + This allows setting the ``pyhf.default_backend`` to be different from the value of |
| 188 | + ``pyhf.tensorlib`` returned by :func:`pyhf.get_backend`, which can be useful in situations |
| 189 | + where differentiable model construction is needed. |
| 190 | + |
| 191 | + .. code:: pycon |
| 192 | +
|
| 193 | + >>> import jax |
| 194 | + >>> import pyhf |
| 195 | + >>> pyhf.set_backend("jax", default=True) |
| 196 | + >>> pyhf.set_backend("numpy") |
| 197 | + >>> pyhf.get_backend() |
| 198 | + (<pyhf.tensor.numpy_backend.numpy_backend object at 0x...>, <pyhf.optimize.scipy_optimizer object at 0x...>) |
| 199 | + >>> pyhf.default_backend |
| 200 | + <pyhf.tensor.jax_backend.jax_backend object at 0x...> |
| 201 | + >>> def example_op(x): |
| 202 | + ... return 2 * pyhf.default_backend.power(pyhf.default_backend.astensor(x), 3) |
| 203 | + ... |
| 204 | + >>> example_op([2.0]) |
| 205 | + DeviceArray([16.], dtype=float64) |
| 206 | + >>> jax.jacrev(jax.jit(example_op))([2.0]) |
| 207 | + [DeviceArray([24.], dtype=float64, weak_type=True)] |
| 208 | +
|
| 209 | +* Schema validation now allows for both :class:`list` and ``pyhf.tensorlib`` objects |
| 210 | + to exist in the model specification. |
| 211 | + (PR :pr:`1647`) |
| 212 | + |
| 213 | + .. code:: pycon |
| 214 | +
|
| 215 | + >>> import pyhf |
| 216 | + >>> signal = pyhf.tensorlib.astensor([12.0, 11.0]) |
| 217 | + >>> background = pyhf.tensorlib.astensor([50.0, 52.0]) |
| 218 | + >>> background_uncertainty = pyhf.tensorlib.astensor([3.0, 7.0]) |
| 219 | + >>> model = pyhf.simplemodels.uncorrelated_background( |
| 220 | + ... signal=signal, bkg=background, bkg_uncertainty=background_uncertainty |
| 221 | + ... ) |
| 222 | +
|
| 223 | +
|
| 224 | +CLI API |
| 225 | +~~~~~~~ |
| 226 | + |
| 227 | +* The ``pyhf xlm2json`` CLI API now has a ``-v/--mount`` option to support reading |
| 228 | + XML configurations with absolute paths. |
| 229 | + (PR :pr:`1909`) |
| 230 | + Similar to Docker volume mounts, the options allows a user to pass two fields |
| 231 | + separated by a colon (``:``). |
| 232 | + The first field is a local path and the second field is the absolute path specified |
| 233 | + in the XML configuration to be substituted. |
| 234 | + Without the ``-v/--mount`` option a user would have to manually edit the absolute |
| 235 | + path in each XML file it appeared in! |
| 236 | + |
| 237 | + .. code:: console |
| 238 | +
|
| 239 | + pyhf xml2json \ |
| 240 | + --mount /local/path/to/workspace:/absolute/path/to/replace/inside/xml \ |
| 241 | + --output-file workspace.json \ |
| 242 | + workspace/analysis_config.xml |
| 243 | +
|
| 244 | +Deprecations |
| 245 | +------------ |
| 246 | + |
| 247 | +Python API |
| 248 | +~~~~~~~~~~ |
| 249 | + |
| 250 | +* The :func:`pyhf.infer.intervals.upperlimit` API has been deprecated in favor of |
| 251 | + :func:`pyhf.infer.intervals.upper_limits.upper_limit`. |
| 252 | + The :func:`pyhf.infer.intervals.upperlimit` API will removed in ``pyhf`` ``v0.9.0``. |
| 253 | + (PR :pr:`1274`) |
| 254 | + |
| 255 | +Removals |
| 256 | +-------- |
| 257 | + |
| 258 | +Python API |
| 259 | +~~~~~~~~~~ |
| 260 | + |
| 261 | +* The :func:`pyhf.simplemodels.hepdata_like` API, deprecated since ``pyhf`` |
| 262 | + ``v0.6.2``, has been removed. |
| 263 | + (PR :pr:`1670`) |
| 264 | + Use the :func:`pyhf.simplemodels.uncorrelated_background` API instead. |
| 265 | + |
| 266 | +* :class:`pyhf.workspace.Workspace`'s ``parameters`` attribute is removed in favor of |
| 267 | + using :class:`pyhf.pdf._ModelConfig`'s ``parameters``. |
| 268 | + (PR :pr:`1625`) |
| 269 | + |
| 270 | +* :func:`pyhf.workspace.Workspace.get_measurement` has the ``poi_name`` kwarg removed. |
| 271 | + (PR :pr:`1636`) |
| 272 | + |
| 273 | +Contributors |
| 274 | +------------ |
| 275 | + |
| 276 | +``v0.7.0`` benefited from contributions from: |
| 277 | + |
| 278 | +* Alexander Held |
| 279 | +* Mason Proffitt |
| 280 | +* Lars Henkelmann |
| 281 | +* Aryan Roy |
| 282 | +* Graeme Watt |
| 283 | +* Jerry Ling |
| 284 | +* Nathan Simpson |
| 285 | +* Beojan Stanislaus |
| 286 | + |
| 287 | +.. |release v0.7.0| replace:: ``v0.7.0`` |
| 288 | +.. _`release v0.7.0`: https://github.com/scikit-hep/pyhf/releases/tag/v0.7.0 |
| 289 | + |
| 290 | +.. _LHC Higgs search combination procedure: https://inspirehep.net/literature/1196797 |
| 291 | +.. |LHC Higgs search combination procedure| replace:: *Procedure for the LHC Higgs boson search combination in Summer 2011* |
0 commit comments