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

Remove deprecated code for 0.7 #1452

Merged
merged 11 commits into from
May 24, 2024
8 changes: 0 additions & 8 deletions docs/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -213,7 +213,6 @@ def setup(app):
# Should come up with better way to address this

from qiskit_experiments.curve_analysis import ParameterRepr
from qiskit_experiments.curve_analysis import SeriesDef


def maybe_skip_member(app, what, name, obj, skip, options):
Expand All @@ -227,9 +226,6 @@ def maybe_skip_member(app, what, name, obj, skip, options):
"y",
"y_err",
"name",
"filter_kwargs",
"fit_func",
"signature",
"artifact_id",
"artifact_data",
"device_components",
Expand All @@ -239,10 +235,6 @@ def maybe_skip_member(app, what, name, obj, skip, options):
skip_members = [
ParameterRepr.repr,
ParameterRepr.unit,
SeriesDef.plot_color,
SeriesDef.plot_symbol,
SeriesDef.model_description,
SeriesDef.canvas,
]
if not skip:
return (name in skip_names or obj in skip_members) and what == "attribute"
Expand Down
2 changes: 1 addition & 1 deletion docs/howtos/artifacts.rst
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ artifacts as a list of :class:`.ArtifactData` objects accessed by :meth:`.Experi
backend = AerSimulator.from_backend(FakePerth())
exp1 = T1(physical_qubits=[0], delays=np.arange(1e-6, 6e-4, 5e-5))
exp2 = T1(physical_qubits=[1], delays=np.arange(1e-6, 6e-4, 5e-5))
data = ParallelExperiment([exp1, exp2], flatten_results=True).run(backend).block_for_results()
data = ParallelExperiment([exp1, exp2]).run(backend).block_for_results()
data.artifacts()

Artifacts can be accessed using either the artifact ID, which has to be unique in each
Expand Down
9 changes: 4 additions & 5 deletions docs/manuals/verification/quantum_volume.rst
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ Extracting the maximum Quantum Volume.
.. jupyter-execute::

qv_values = [
batch_expdata.child_data(i).analysis_results("quantum_volume").value
batch_expdata.analysis_results("quantum_volume")[i].value
for i in range(batch_exp.num_experiments)
]

Expand All @@ -169,10 +169,9 @@ Extracting the maximum Quantum Volume.

for i in range(batch_exp.num_experiments):
print(f"\nComponent experiment {i}")
sub_data = batch_expdata.child_data(i)
display(sub_data.figure(0))
for result in sub_data.analysis_results():
print(result)
display(batch_expdata.figure(i))
for result in batch_expdata.analysis_results():
print(result)

References
----------
Expand Down
3 changes: 1 addition & 2 deletions docs/manuals/verification/randomized_benchmarking.rst
Original file line number Diff line number Diff line change
Expand Up @@ -182,8 +182,7 @@ The EPGs of two-qubit RB are analyzed with the corrected EPC if available.
[
StandardRB((qubit,), lengths_1_qubit, num_samples=num_samples, seed=seed)
for qubit in qubits
],
flatten_results=True,
]
)
expdata_1q = single_exps.run(backend).block_for_results()

Expand Down
13 changes: 4 additions & 9 deletions docs/tutorials/curve_analysis.rst
Original file line number Diff line number Diff line change
Expand Up @@ -343,7 +343,7 @@ For example, :class:`.StarkRamseyXYAmpScanAnalysis` defines four `series`
labels in its ``data_subfit_map`` option (``Xpos``, ``Ypos``, ``Xneg``,
``Yneg``) but only two models (``FREQpos``, ``FREQneg``) whose names do not
match the series labels.
It does this by overriding the ``CurveData._format_data()`` method and adding
It does this by overriding the ``CurveAnalysis._format_data()`` method and adding
its own series to the :class:`.ScatterTable` with series labels to match its
fit model names (by combining ``Xpos`` and ``Ypos`` series data into a
``FREQpos`` series and similary for the series with names ending with ``neg``).
Expand Down Expand Up @@ -400,11 +400,6 @@ See the :doc:`Artifacts how-to </howtos/artifacts>` for more information.
Curve Analysis workflow
-----------------------

.. warning::

:class:`CurveData` dataclass is replaced with :class:`.ScatterTable` dataframe.
This class will be deprecated and removed in the future release.

Typically curve analysis performs fitting as follows.
This workflow is defined in the method :meth:`CurveAnalysis._run_analysis`.

Expand Down Expand Up @@ -534,9 +529,9 @@ one can get the list of parameters with the :attr:`CurveAnalysis.parameters`. Ea
boundary value can be a tuple of floats representing minimum and maximum values.

Apart from user provided guesses, the analysis can systematically generate those values
with the method :meth:`_generate_fit_guesses`, which is called with the :class:`CurveData`
dataclass. If the analysis contains multiple model definitions, we can get the subset
of curve data with :meth:`.CurveData.get_subset_of` using the name of the series. A
with the method :meth:`_generate_fit_guesses`, which is called with the :class:`.ScatterTable`
class. If the analysis contains multiple model definitions, we can get the subset
of curve data with :meth:`.ScatterTable.get_subset_of` using the name of the series. A
developer can implement the algorithm to generate initial guesses and boundaries by
using this curve data object, which will be provided to the fitter. Note that there are
several common initial guess estimators available in :mod:`curve_analysis.guess`.
Expand Down
28 changes: 6 additions & 22 deletions docs/tutorials/getting_started.rst
Original file line number Diff line number Diff line change
Expand Up @@ -384,7 +384,7 @@ simultaneously on the same device:

child_exp1 = T1(physical_qubits=(2,), delays=delays)
child_exp2 = StandardRB(physical_qubits=(3,1), lengths=np.arange(1,100,10), num_samples=2)
parallel_exp = ParallelExperiment([child_exp1, child_exp2], flatten_results=False)
parallel_exp = ParallelExperiment([child_exp1, child_exp2])

Note that when the transpile and run options are set for a composite experiment, the
child experiments's options are also set to the same options recursively. Let's examine
Expand Down Expand Up @@ -437,35 +437,19 @@ arbitrarily to make complex composite experiments.
Viewing child experiment data
-----------------------------

The experiment data returned from a composite experiment contains individual analysis
results for each child experiment that can be accessed using
:meth:`~.ExperimentData.child_data`. By default, the parent data object does not contain
analysis results.
The experiment data returned from a composite experiment contains analysis
results for each child experiment in the parent experiment.

.. note::

This behavior will be updated in Qiskit Experiments 0.7.
By default, all analysis results will be stored in the parent data object,
and you need to explicitly set ``flatten_results=False`` to generate child data objects.

.. jupyter-execute::

parallel_data = parallel_exp.run(backend, seed_simulator=101).block_for_results()

for i, sub_data in enumerate(parallel_data.child_data()):
print("Component experiment",i)
display(sub_data.figure(0))
for result in sub_data.analysis_results():
print(result)

If you want the parent data object to contain the analysis results instead, you can set
the ``flatten_results`` flag to true to flatten the results of all component experiments
into one level:
and you need to explicitly set ``flatten_results=False`` to generate child
data objects in the legacy format.

.. jupyter-execute::

parallel_exp = ParallelExperiment(
[T1(physical_qubits=(i,), delays=delays) for i in range(2)], flatten_results=True
[T1(physical_qubits=(i,), delays=delays) for i in range(2)]
)
parallel_data = parallel_exp.run(backend, seed_simulator=101).block_for_results()

Expand Down
18 changes: 0 additions & 18 deletions qiskit_experiments/curve_analysis/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,21 +40,10 @@
:toctree: ../stubs/

ScatterTable
SeriesDef
CurveData
CurveFitResult
ParameterRepr
FitOptions

Visualization
=============

.. autosummary::
:toctree: ../stubs/

BaseCurveDrawer
MplCurveDrawer

Standard Analysis Library
=========================

Expand Down Expand Up @@ -120,18 +109,14 @@
from .composite_curve_analysis import CompositeCurveAnalysis
from .scatter_table import ScatterTable
from .curve_data import (
CurveData,
CurveFitResult,
FitData,
FitOptions,
ParameterRepr,
SeriesDef,
)
from .curve_fit import (
process_curve_data,
process_multi_curve_data,
)
from .visualization import BaseCurveDrawer, MplCurveDrawer
from . import guess
from . import fit_function
from . import utils
Expand All @@ -146,6 +131,3 @@
ErrorAmplificationAnalysis,
BlochTrajectoryAnalysis,
)

# deprecated
from .visualization import plot_curve_fit, plot_errorbar, plot_scatter, FitResultPlotters
39 changes: 0 additions & 39 deletions qiskit_experiments/curve_analysis/base_curve_analysis.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,11 @@
Base class of curve analysis.
"""

import warnings
from abc import ABC, abstractmethod
from typing import Dict, List, Union

import lmfit

from qiskit.utils.deprecation import deprecate_func

from qiskit_experiments.data_processing import DataProcessor
from qiskit_experiments.data_processing.processor_library import get_processor
from qiskit_experiments.framework import (
Expand All @@ -31,10 +28,8 @@
Options,
)
from qiskit_experiments.visualization import (
BaseDrawer,
BasePlotter,
CurvePlotter,
LegacyCurveCompatDrawer,
MplDrawer,
)

Expand Down Expand Up @@ -130,20 +125,6 @@ def plotter(self) -> BasePlotter:
"""A short-cut to the curve plotter instance."""
return self._options.plotter

@property
@deprecate_func(
since="0.5",
additional_msg="Use `plotter` from the new visualization module.",
removal_timeline="after 0.6",
package_name="qiskit-experiments",
)
def drawer(self) -> BaseDrawer:
"""A short-cut for curve drawer instance, if set. ``None`` otherwise."""
if isinstance(self.plotter.drawer, LegacyCurveCompatDrawer):
return self.plotter.drawer._curve_drawer
else:
return None

@classmethod
def _default_options(cls) -> Options:
"""Return default analysis options.
Expand All @@ -159,8 +140,6 @@ def _default_options(cls) -> Options:
not create a figure. This overrides the behavior of ``generate_figures``.
return_fit_parameters (bool): (Deprecated) Set ``True`` to return all fit model parameters
with details of the fit outcome. Default to ``False``.
return_data_points (bool): (Deprecated) Set ``True`` to include in the analysis result
the formatted data points given to the fitter. Default to ``False``.
data_processor (Callable): A callback function to format experiment data.
This can be a :class:`.DataProcessor`
instance that defines the `self.__call__` method.
Expand Down Expand Up @@ -211,7 +190,6 @@ def _default_options(cls) -> Options:
options.plot_raw_data = False
options.plot_residuals = False
options.return_fit_parameters = True
options.return_data_points = False
options.data_processor = None
options.normalization = False
options.average_method = "shots_weighted"
Expand Down Expand Up @@ -405,20 +383,3 @@ def _initialize(
if not data_processor.is_trained:
data_processor.train(data=experiment_data.data())
self.set_options(data_processor=data_processor)

# Check if a model contains legacy data mapping option.
data_subfit_map = {}
for model in self.models:
if "data_sort_key" in model.opts:
data_subfit_map[model._name] = model.opts["data_sort_key"]
del model.opts["data_sort_key"]
if data_subfit_map:
warnings.warn(
"Setting 'data_sort_key' to an LMFIT model constructor is no longer "
"valid configuration of the model. "
"Use 'data_subfit_map' option in the analysis options. "
"This warning will be dropped in v0.6 along with the support for the "
"'data_sort_key' in the LMFIT model options.",
DeprecationWarning,
)
self.set_options(data_subfit_map=data_subfit_map)
48 changes: 1 addition & 47 deletions qiskit_experiments/curve_analysis/composite_curve_analysis.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,19 +22,15 @@
import numpy as np
import pandas as pd

from qiskit.utils.deprecation import deprecate_func

from qiskit_experiments.framework import (
AnalysisResultData,
BaseAnalysis,
ExperimentData,
Options,
)
from qiskit_experiments.visualization import (
BaseDrawer,
BasePlotter,
CurvePlotter,
LegacyCurveCompatDrawer,
MplDrawer,
)

Expand Down Expand Up @@ -76,7 +72,6 @@ class CompositeCurveAnalysis(BaseAnalysis):
for qi in (0, 1):
analysis = curve.OscillationAnalysis(name=f"init{qi}")
analysis.set_options(
return_fit_parameters=["freq"],
filter_data={"init_state": qi},
)
analysis = CompositeCurveAnalysis(analyses=analyses)
Expand Down Expand Up @@ -147,20 +142,6 @@ def plotter(self) -> BasePlotter:
"""A short-cut to the plotter instance."""
return self._options.plotter

@property
@deprecate_func(
since="0.5",
additional_msg="Use `plotter` from the new visualization module instead.",
removal_timeline="after 0.6",
package_name="qiskit-experiments",
)
def drawer(self) -> BaseDrawer:
"""A short-cut for curve drawer instance, if set. ``None`` otherwise."""
if hasattr(self._options, "curve_drawer"):
return self._options.curve_drawer
else:
return None

def analyses(
self, index: Optional[Union[str, int]] = None
) -> Union[BaseCurveAnalysis, List[BaseCurveAnalysis]]:
Expand Down Expand Up @@ -273,8 +254,6 @@ def _default_options(cls) -> Options:
This is ``True`` by default.
return_fit_parameters (bool): (Deprecated) Set ``True`` to return all fit model parameters
with details of the fit outcome. Default to ``False``.
return_data_points (bool): (Deprecated) Set ``True`` to include in the analysis result
the formatted data points given to the fitter. Default to ``False``.
extra (Dict[str, Any]): A dictionary that is appended to all database entries
as extra information.
"""
Expand All @@ -283,7 +262,6 @@ def _default_options(cls) -> Options:
plotter=CurvePlotter(MplDrawer()),
plot=True,
return_fit_parameters=False,
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
return_fit_parameters=False,
return_fit_parameters=True,

I think this has been True because options value comes from the base class. For example Ham tomo experiment has returned the fit parameter (in the unittest we just don't search by index)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm I ran ham tomo on current code but didn't see the fit parameter:
image
You think we should change this behavior? I don't remember why return_fit_parameters was set to false for composite curve analysis.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I realized we unintentionally introduced breaking API change in the previous release.
https://github.com/Qiskit-Extensions/qiskit-experiments/blob/bc0b89e0eeedfabab7de2d5b6c5472e26bdbfb5a/qiskit_experiments/curve_analysis/composite_curve_analysis.py#L373-L375
We should have duplicated this combined_summary in the analysis results, but we only added this to artifact of the composite curve analysis. So the data has been moved to artifact without any warning. So far we didn't see any report in our issue, and I think this bug is not enough serious to motivate us to make a patch release for 0.6. And we don't need to redefine return_fit_parameters in the composite curve analysis options. What do you think?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, thanks for finding the source of the problem. How about I just keep the code the same and add a note in the Known Issues section of the release notes?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds good to me!

return_data_points=False,
extra={},
)

Expand All @@ -293,27 +271,6 @@ def _default_options(cls) -> Options:
return options

def set_options(self, **fields):
# TODO remove this in Qiskit Experiments 0.6
if "curve_drawer" in fields:
warnings.warn(
"The option 'curve_drawer' is replaced with 'plotter'. "
"This option will be removed in Qiskit Experiments 0.6.",
DeprecationWarning,
stacklevel=2,
)
# Set the plotter drawer to `curve_drawer`. If `curve_drawer` is the right type, set it
# directly. If not, wrap it in a compatibility drawer.
if isinstance(fields["curve_drawer"], BaseDrawer):
plotter = self.options.plotter
plotter.drawer = fields.pop("curve_drawer")
fields["plotter"] = plotter
else:
drawer = fields["curve_drawer"]
compat_drawer = LegacyCurveCompatDrawer(drawer)
plotter = self.options.plotter
plotter.drawer = compat_drawer
fields["plotter"] = plotter

for field in fields:
if not hasattr(self.options, field):
warnings.warn(
Expand Down Expand Up @@ -349,10 +306,7 @@ def _run_analysis(
metadata = analysis.options.extra
metadata["group"] = analysis.name
analysis.set_options(
plot=False,
extra=metadata,
return_fit_parameters=self.options.return_fit_parameters,
return_data_points=self.options.return_data_points,
plot=False, extra=metadata, return_fit_parameters=self.options.return_fit_parameters
)
results, _ = analysis._run_analysis(experiment_data)
for res in results:
Expand Down
Loading
Loading