Skip to content

Commit e5ff8ad

Browse files
committed
Add AnalysisResult class
- AnalysisResultData class has been deprecated - ExperimentData.load is updated to directly instantiate own class - DbExperimentData._analysis_res_cls attribute is added to instantiate proper analysis container AnalysisResult class implements _from_service_data method that implements formatter for FitVal. UFloat value is converted into FitVal just before data saving and converted back into UFloat in the loader. Covariance info will be lost in round trip. FitVal is still supported as value container for UFloat in database service.
1 parent 266ef45 commit e5ff8ad

File tree

22 files changed

+573
-121
lines changed

22 files changed

+573
-121
lines changed

qiskit_experiments/curve_analysis/curve_analysis.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@
4343
from qiskit_experiments.framework import (
4444
BaseAnalysis,
4545
ExperimentData,
46-
AnalysisResultData,
46+
AnalysisResult,
4747
Options,
4848
)
4949

@@ -203,7 +203,7 @@ class AnalysisExample(CurveAnalysis):
203203
204204
- Create extra data from fit result:
205205
Override :meth:`~self._extra_database_entry`. You need to return a list of
206-
:class:`~qiskit_experiments.framework.analysis_result_data.AnalysisResultData`
206+
:class:`~qiskit_experiments.framework.analysis_result_data.AnalysisResult`
207207
object. This returns an empty list by default.
208208
209209
- Customize fit quality evaluation:
@@ -496,7 +496,7 @@ def _format_data(self, data: CurveData) -> CurveData:
496496
)
497497

498498
# pylint: disable=unused-argument
499-
def _extra_database_entry(self, fit_data: FitData) -> List[AnalysisResultData]:
499+
def _extra_database_entry(self, fit_data: FitData) -> List[AnalysisResult]:
500500
"""Calculate new quantity from the fit result.
501501
502502
Subclasses can override this method to do post analysis.
@@ -746,7 +746,7 @@ def _data(
746746

747747
def _run_analysis(
748748
self, experiment_data: ExperimentData
749-
) -> Tuple[List[AnalysisResultData], List["pyplot.Figure"]]:
749+
) -> Tuple[List[AnalysisResult], List["pyplot.Figure"]]:
750750
#
751751
# 1. Parse arguments
752752
#
@@ -868,7 +868,7 @@ def _run_analysis(
868868

869869
# overview entry
870870
analysis_results.append(
871-
AnalysisResultData(
871+
AnalysisResult(
872872
name=PARAMS_ENTRY_PREFIX + self.__class__.__name__,
873873
value=[p.nominal_value for p in fit_result.popt],
874874
chisq=fit_result.reduced_chisq,
@@ -895,7 +895,7 @@ def _run_analysis(
895895
p_name = param_repr
896896
p_repr = param_repr
897897
unit = None
898-
result_entry = AnalysisResultData(
898+
result_entry = AnalysisResult(
899899
name=p_repr,
900900
value=fit_result.fitval(p_name),
901901
unit=unit,
@@ -918,7 +918,7 @@ def _run_analysis(
918918
"ydata": series_data.y,
919919
"sigma": series_data.y_err,
920920
}
921-
raw_data_entry = AnalysisResultData(
921+
raw_data_entry = AnalysisResult(
922922
name=DATA_ENTRY_PREFIX + self.__class__.__name__,
923923
value=raw_data_dict,
924924
extra={

qiskit_experiments/curve_analysis/visualization/fit_result_plotters.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@
3030
from qiskit.utils import detach_prefix
3131

3232
from qiskit_experiments.curve_analysis.curve_data import SeriesDef, FitData, CurveData
33-
from qiskit_experiments.framework import AnalysisResultData
33+
from qiskit_experiments.framework import AnalysisResult
3434
from qiskit_experiments.framework.matplotlib import get_non_gui_ax
3535
from .curves import plot_scatter, plot_errorbar, plot_curve_fit
3636
from .style import PlotterStyle
@@ -47,7 +47,7 @@ def draw(
4747
fit_samples: List[CurveData],
4848
tick_labels: Dict[str, str],
4949
fit_data: FitData,
50-
result_entries: List[AnalysisResultData],
50+
result_entries: List[AnalysisResult],
5151
style: Optional[PlotterStyle] = None,
5252
axis: Optional["matplotlib.axes.Axes"] = None,
5353
) -> "pyplot.Figure":
@@ -146,7 +146,7 @@ def draw(
146146
fit_samples: List[CurveData],
147147
tick_labels: Dict[str, str],
148148
fit_data: FitData,
149-
result_entries: List[AnalysisResultData],
149+
result_entries: List[AnalysisResult],
150150
style: Optional[PlotterStyle] = None,
151151
axis: Optional["matplotlib.axes.Axes"] = None,
152152
) -> "pyplot.Figure":
@@ -336,7 +336,7 @@ def draw_single_curve_mpl(
336336
)
337337

338338

339-
def write_fit_report(result_entries: List[AnalysisResultData]) -> str:
339+
def write_fit_report(result_entries: List[AnalysisResult]) -> str:
340340
"""A function that generates fit reports documentation from list of data.
341341
342342
Args:

qiskit_experiments/database_service/db_analysis_result.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -203,7 +203,7 @@ def save(self) -> None:
203203

204204
def copy(self) -> "DbAnalysisResultV1":
205205
"""Return a copy of the result with a new result ID"""
206-
return DbAnalysisResultV1(
206+
return self.__class__(
207207
name=self.name,
208208
value=self.value,
209209
device_components=self.device_components,

qiskit_experiments/database_service/db_experiment_data.py

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,7 @@ class DbExperimentDataV1(DbExperimentData):
128128
verbose = True # Whether to print messages to the standard output.
129129
_metadata_version = 1
130130
_job_executor = futures.ThreadPoolExecutor()
131+
_analysis_res_cls = DbAnalysisResult
131132

132133
_json_encoder = ExperimentEncoder
133134
_json_decoder = ExperimentDecoder
@@ -812,7 +813,7 @@ def _retrieve_analysis_results(self, refresh: bool = False):
812813
)
813814
for result in retrieved_results:
814815
result_id = result["result_id"]
815-
self._analysis_results[result_id] = DbAnalysisResult._from_service_data(result)
816+
self._analysis_results[result_id] = self._analysis_res_cls._from_service_data(result)
816817

817818
def analysis_results(
818819
self,
@@ -1008,18 +1009,15 @@ def load(cls, experiment_id: str, service: DatabaseServiceV1) -> "DbExperimentDa
10081009
service_data = service.experiment(experiment_id, json_decoder=cls._json_decoder)
10091010

10101011
# Parse serialized metadata
1011-
metadata = service_data.pop("metadata")
1012-
1013-
# Initialize container
1014-
expdata = DbExperimentDataV1(
1012+
expdata = cls(
10151013
experiment_type=service_data.pop("experiment_type"),
10161014
backend=service_data.pop("backend"),
10171015
experiment_id=service_data.pop("experiment_id"),
10181016
parent_id=service_data.pop("parent_id", None),
10191017
tags=service_data.pop("tags"),
10201018
job_ids=service_data.pop("job_ids"),
10211019
share_level=service_data.pop("share_level"),
1022-
metadata=metadata,
1020+
metadata=service_data.pop("metadata"),
10231021
figure_names=service_data.pop("figure_names"),
10241022
notes=service_data.pop("notes"),
10251023
**service_data,

qiskit_experiments/database_service/db_fitval.py

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313
"""DB class for fit value with std error and unit."""
1414

1515
import dataclasses
16-
import warnings
1716
from typing import Optional
1817

1918

@@ -34,11 +33,3 @@ def __str__(self):
3433
if self.unit is not None:
3534
out += f" {str(self.unit)}"
3635
return out
37-
38-
39-
def __new__(cls, *args, **kwargs):
40-
warnings.warn(
41-
"FitVal object has been deprecated in Qiskit Experiments version 0.3 and "
42-
"will be removed in version 0.5. Use version <= 0.3 to load this object.",
43-
DeprecationWarning,
44-
)

qiskit_experiments/database_service/device_component.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212

1313
"""Device component classes."""
1414

15+
from typing import Dict, Any
1516
from abc import ABC, abstractmethod
1617

1718

@@ -35,6 +36,15 @@ def __init__(self, index: int):
3536
def __str__(self):
3637
return f"Q{self._index}"
3738

39+
def __json_encode__(self):
40+
"""Convert to format that can be JSON serialized."""
41+
return {"index": self._index}
42+
43+
@classmethod
44+
def __json_decode__(cls, value: Dict[str, Any]) -> "Qubit":
45+
"""Load from JSON compatible format."""
46+
return cls(**value)
47+
3848

3949
class Resonator(DeviceComponent):
4050
"""Class representing a resonator device component."""
@@ -45,6 +55,15 @@ def __init__(self, index: int):
4555
def __str__(self):
4656
return f"R{self._index}"
4757

58+
def __json_encode__(self):
59+
"""Convert to format that can be JSON serialized."""
60+
return {"index": self._index}
61+
62+
@classmethod
63+
def __json_decode__(cls, value: Dict[str, Any]) -> "Resonator":
64+
"""Load from JSON compatible format."""
65+
return cls(**value)
66+
4867

4968
class UnknownComponent(DeviceComponent):
5069
"""Class representing unknown device component."""
@@ -55,6 +74,15 @@ def __init__(self, component: str):
5574
def __str__(self):
5675
return self._component
5776

77+
def __json_encode__(self):
78+
"""Convert to format that can be JSON serialized."""
79+
return {"component": self._component}
80+
81+
@classmethod
82+
def __json_decode__(cls, value: Dict[str, Any]) -> "UnknownComponent":
83+
"""Load from JSON compatible format."""
84+
return cls(**value)
85+
5886

5987
def to_component(string: str) -> DeviceComponent:
6088
"""Convert the input string to a ``DeviceComponent`` instance.

qiskit_experiments/framework/__init__.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -187,7 +187,7 @@
187187
188188
The :meth:`BaseAnalysis._run_analysis` method should return a pair
189189
``(results, figures)`` where ``results`` is a list of
190-
:class:`AnalysisResultData` and ``figures`` is a list of
190+
:class:`AnalysisResult` and ``figures`` is a list of
191191
:class:`matplotlib.figure.Figure`.
192192
193193
The :mod:`qiskit_experiments.data_processing` module contains classes for
@@ -207,6 +207,7 @@
207207
JobStatus
208208
AnalysisStatus
209209
FitVal
210+
AnalysisResult
210211
AnalysisResultData
211212
ExperimentConfig
212213
AnalysisConfig
@@ -246,7 +247,7 @@
246247
from .base_analysis import BaseAnalysis
247248
from .base_experiment import BaseExperiment
248249
from .configs import ExperimentConfig, AnalysisConfig
249-
from .analysis_result_data import AnalysisResultData
250+
from .analysis_result_data import AnalysisResultData, AnalysisResult
250251
from .experiment_data import ExperimentData
251252
from .composite import (
252253
ParallelExperiment,

0 commit comments

Comments
 (0)