From 9bece70f7f3a7bde0462761a5c01f6f17b18c812 Mon Sep 17 00:00:00 2001 From: Steve Wood <40241007+woodsp-ibm@users.noreply.github.com> Date: Tue, 6 Feb 2024 05:19:40 -0500 Subject: [PATCH] Add slow_test as it's no longer part of Qiskit 1.0 (#141) (cherry picked from commit 22452888e3b3cb5a8b2f08c7e262c5b8ec4bbdc4) # Conflicts: # test/optimizers/test_optimizer_aqgd.py --- test/__init__.py | 5 ++- test/decorators.py | 37 +++++++++++++++++++ test/eigensolvers/test_vqd.py | 22 +++++------ test/gradients/test_estimator_gradient.py | 5 +-- .../minimum_eigensolvers/test_sampling_vqe.py | 21 +++++------ test/minimum_eigensolvers/test_vqe.py | 3 +- test/optimizers/test_optimizer_aqgd.py | 7 +++- test/time_evolvers/test_pvqd.py | 4 +- 8 files changed, 71 insertions(+), 33 deletions(-) create mode 100644 test/decorators.py diff --git a/test/__init__.py b/test/__init__.py index 7c8e5483..5df17da8 100644 --- a/test/__init__.py +++ b/test/__init__.py @@ -1,6 +1,6 @@ # This code is part of a Qiskit project. # -# (C) Copyright IBM 2018, 2023. +# (C) Copyright IBM 2018, 2024. # # This code is licensed under the Apache License, Version 2.0. You may # obtain a copy of this license in the LICENSE.txt file in the root directory @@ -13,5 +13,6 @@ """Algorithms test module""" from .algorithms_test_case import QiskitAlgorithmsTestCase +from .decorators import slow_test -__all__ = ["QiskitAlgorithmsTestCase"] +__all__ = ["QiskitAlgorithmsTestCase", "slow_test"] diff --git a/test/decorators.py b/test/decorators.py new file mode 100644 index 00000000..e14a3ba2 --- /dev/null +++ b/test/decorators.py @@ -0,0 +1,37 @@ +# This code is part of a Qiskit project. +# +# (C) Copyright IBM 2017, 2024. +# +# This code is licensed under the Apache License, Version 2.0. You may +# obtain a copy of this license in the LICENSE.txt file in the root directory +# of this source tree or at http://www.apache.org/licenses/LICENSE-2.0. +# +# Any modifications or derivative works of this code must retain this +# copyright notice, and modified files need to carry a notice indicating +# that they have been altered from the originals. + + +"""Decorator for using with unit tests.""" + +import functools +import os +import unittest + + +def slow_test(func): + """Decorator that signals that the test takes minutes to run. + + Args: + func (callable): test function to be decorated. + + Returns: + callable: the decorated function. + """ + + @functools.wraps(func) + def _wrapper(*args, **kwargs): + if "run_slow" in os.environ.get("QISKIT_TESTS", ""): + raise unittest.SkipTest("Skipping slow tests") + return func(*args, **kwargs) + + return _wrapper diff --git a/test/eigensolvers/test_vqd.py b/test/eigensolvers/test_vqd.py index 46b22a31..78b398c6 100644 --- a/test/eigensolvers/test_vqd.py +++ b/test/eigensolvers/test_vqd.py @@ -1,6 +1,6 @@ # This code is part of a Qiskit project. # -# (C) Copyright IBM 2022, 2023. +# (C) Copyright IBM 2022, 2024. # # This code is licensed under the Apache License, Version 2.0. You may # obtain a copy of this license in the LICENSE.txt file in the root directory @@ -22,7 +22,6 @@ from qiskit.circuit.library import TwoLocal, RealAmplitudes from qiskit.primitives import Sampler, Estimator from qiskit.quantum_info import SparsePauliOp -from qiskit.quantum_info.operators import Operator from qiskit_algorithms.eigensolvers import VQD, VQDResult from qiskit_algorithms import AlgorithmError @@ -39,7 +38,6 @@ ("XX", 0.18093119978423156), ] ) -H2_OP = Operator(H2_SPARSE_PAULI.to_matrix()) @ddt @@ -64,7 +62,7 @@ def setUp(self): self.fidelity = ComputeUncompute(Sampler()) self.betas = [50, 50] - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_basic_operator(self, op): """Test the VQD without aux_operators.""" wavefunction = self.ryrz_wavefunction @@ -127,7 +125,7 @@ def test_beta_autoeval(self, op): beta = float(logs.output[0].split()[-1]) self.assertAlmostEqual(beta, 20.40459399499687, 4) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_mismatching_num_qubits(self, op): """Ensuring circuit and operator mismatch is caught""" wavefunction = QuantumCircuit(1) @@ -143,7 +141,7 @@ def test_mismatching_num_qubits(self, op): with self.assertRaises(AlgorithmError): _ = vqd.compute_eigenvalues(operator=op) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_missing_varform_params(self, op): """Test specifying a variational form with no parameters raises an error.""" circuit = QuantumCircuit(op.num_qubits) @@ -158,7 +156,7 @@ def test_missing_varform_params(self, op): with self.assertRaises(AlgorithmError): vqd.compute_eigenvalues(operator=op) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_callback(self, op): """Test the callback on VQD.""" history = {"eval_count": [], "parameters": [], "mean": [], "metadata": [], "step": []} @@ -202,7 +200,7 @@ def store_intermediate_result(eval_count, parameters, mean, metadata, step): np.testing.assert_array_almost_equal(history["mean"], ref_mean, decimal=2) np.testing.assert_array_almost_equal(history["step"], ref_step, decimal=0) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_vqd_optimizer(self, op): """Test running same VQD twice to re-use optimizer, then switch optimizer""" @@ -241,7 +239,7 @@ def run_check(): result = vqd.compute_eigenvalues(operator=op) self.assertIsInstance(result, VQDResult) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_optimizer_list(self, op): """Test sending an optimizer list""" @@ -281,7 +279,7 @@ def test_optimizer_list(self, op): result.eigenvalues.real, self.h2_energy_excited[:2], decimal=3 ) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_aux_operators_list(self, op): """Test list-based aux_operators.""" wavefunction = self.ry_wavefunction @@ -334,7 +332,7 @@ def test_aux_operators_list(self, op): self.assertIsInstance(result.aux_operators_evaluated[0][1][1], dict) self.assertIsInstance(result.aux_operators_evaluated[0][3][1], dict) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_aux_operators_dict(self, op): """Test dictionary compatibility of aux_operators""" wavefunction = self.ry_wavefunction @@ -388,7 +386,7 @@ def test_aux_operators_dict(self, op): self.assertIsInstance(result.aux_operators_evaluated[0]["aux_op2"][1], dict) self.assertIsInstance(result.aux_operators_evaluated[0]["zero_operator"][1], dict) - @data(H2_OP, H2_SPARSE_PAULI) + @data(H2_SPARSE_PAULI) def test_aux_operator_std_dev(self, op): """Test non-zero standard deviations of aux operators.""" wavefunction = self.ry_wavefunction diff --git a/test/gradients/test_estimator_gradient.py b/test/gradients/test_estimator_gradient.py index 975cb9bf..2a90559f 100644 --- a/test/gradients/test_estimator_gradient.py +++ b/test/gradients/test_estimator_gradient.py @@ -24,7 +24,7 @@ from qiskit.circuit.library import EfficientSU2, RealAmplitudes from qiskit.circuit.library.standard_gates import RXXGate, RYYGate, RZXGate, RZZGate from qiskit.primitives import Estimator -from qiskit.quantum_info import Operator, SparsePauliOp, Pauli +from qiskit.quantum_info import SparsePauliOp, Pauli from qiskit.quantum_info.random import random_pauli_list from qiskit_algorithms.gradients import ( @@ -70,9 +70,6 @@ def test_gradient_operators(self, grad): op = SparsePauliOp.from_list([("Z", 1)]) value = gradient.run([qc], [op], [param]).result().gradients[0] self.assertAlmostEqual(value[0], correct_result, 3) - op = Operator.from_label("Z") - value = gradient.run([qc], [op], [param]).result().gradients[0] - self.assertAlmostEqual(value[0], correct_result, 3) @data(*gradient_factories) def test_single_circuit_observable(self, grad): diff --git a/test/minimum_eigensolvers/test_sampling_vqe.py b/test/minimum_eigensolvers/test_sampling_vqe.py index 3ae889fc..35b84a3a 100644 --- a/test/minimum_eigensolvers/test_sampling_vqe.py +++ b/test/minimum_eigensolvers/test_sampling_vqe.py @@ -1,6 +1,6 @@ # This code is part of a Qiskit project. # -# (C) Copyright IBM 2018, 2023. +# (C) Copyright IBM 2018, 2024. # # This code is licensed under the Apache License, Version 2.0. You may # obtain a copy of this license in the LICENSE.txt file in the root directory @@ -24,7 +24,7 @@ from qiskit.circuit import ParameterVector, QuantumCircuit from qiskit.circuit.library import RealAmplitudes, TwoLocal from qiskit.primitives import Sampler -from qiskit.quantum_info import Operator, Pauli, SparsePauliOp +from qiskit.quantum_info import Pauli, SparsePauliOp from qiskit_algorithms import AlgorithmError from qiskit_algorithms.minimum_eigensolvers import SamplingVQE @@ -50,7 +50,6 @@ def _mock_optimizer(fun, x0, jac=None, bounds=None, inputs=None): PAULI_OP = SparsePauliOp(["ZZ", "IZ", "II"], coeffs=[1, -0.5, 0.12]) -OP = Operator(PAULI_OP.to_matrix()) @ddt @@ -63,7 +62,7 @@ def setUp(self): self.optimal_bitstring = "10" algorithm_globals.random_seed = 42 - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_exact_sampler(self, op): """Test the VQE on BasicAer's statevector simulator.""" thetas = ParameterVector("th", 4) @@ -102,7 +101,7 @@ def test_exact_sampler(self, op): self.assertEqual(result.best_measurement["bitstring"], self.optimal_bitstring) self.assertEqual(result.best_measurement["value"], self.optimal_value) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_invalid_initial_point(self, op): """Test the proper error is raised when the initial point has the wrong size.""" ansatz = RealAmplitudes(2, reps=1) @@ -113,7 +112,7 @@ def test_invalid_initial_point(self, op): with self.assertRaises(ValueError): _ = vqe.compute_minimum_eigenvalue(operator=op) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_ansatz_resize(self, op): """Test the ansatz is properly resized if it's a blueprint circuit.""" ansatz = RealAmplitudes(1, reps=1) @@ -121,7 +120,7 @@ def test_ansatz_resize(self, op): result = vqe.compute_minimum_eigenvalue(operator=op) self.assertAlmostEqual(result.eigenvalue, self.optimal_value, places=5) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_invalid_ansatz_size(self, op): """Test an error is raised if the ansatz has the wrong number of qubits.""" ansatz = QuantumCircuit(1) @@ -131,7 +130,7 @@ def test_invalid_ansatz_size(self, op): with self.assertRaises(AlgorithmError): _ = vqe.compute_minimum_eigenvalue(operator=op) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_missing_varform_params(self, op): """Test specifying a variational form with no parameters raises an error.""" circuit = QuantumCircuit(op.num_qubits) @@ -139,7 +138,7 @@ def test_missing_varform_params(self, op): with self.assertRaises(AlgorithmError): vqe.compute_minimum_eigenvalue(operator=op) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_batch_evaluate_slsqp(self, op): """Test batching with SLSQP (as representative of SciPyOptimizer).""" optimizer = SLSQP(max_evals_grouped=10) @@ -198,7 +197,7 @@ def test_optimizer_callable(self): result = vqe.compute_minimum_eigenvalue(Pauli("Z")) self.assertTrue(np.all(result.optimal_point == np.zeros(ansatz.num_parameters))) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_auxops(self, op): """Test passing auxiliary operators.""" ansatz = RealAmplitudes(2, reps=1) @@ -226,7 +225,7 @@ def test_nondiag_observable_raises(self): with self.assertRaises(ValueError): _ = vqe.compute_minimum_eigenvalue(Pauli("X")) - @data(PAULI_OP, OP) + @data(PAULI_OP) def test_callback(self, op): """Test the callback on VQE.""" history = { diff --git a/test/minimum_eigensolvers/test_vqe.py b/test/minimum_eigensolvers/test_vqe.py index 8d5f48b1..d71bec9b 100644 --- a/test/minimum_eigensolvers/test_vqe.py +++ b/test/minimum_eigensolvers/test_vqe.py @@ -1,6 +1,6 @@ # This code is part of a Qiskit project. # -# (C) Copyright IBM 2022, 2023. +# (C) Copyright IBM 2022, 2024. # # This code is licensed under the Apache License, Version 2.0. You may # obtain a copy of this license in the LICENSE.txt file in the root directory @@ -245,6 +245,7 @@ def test_reuse(self): self.assertAlmostEqual(result.eigenvalue.real, self.h2_energy, places=5) operator = Operator(np.array([[1, 0, 0, 0], [0, -1, 0, 0], [0, 0, 2, 0], [0, 0, 0, 3]])) + operator = SparsePauliOp.from_operator(operator) with self.subTest(msg="assert vqe works on re-use."): result = vqe.compute_minimum_eigenvalue(operator=operator) diff --git a/test/optimizers/test_optimizer_aqgd.py b/test/optimizers/test_optimizer_aqgd.py index c2136a95..8a58ba71 100644 --- a/test/optimizers/test_optimizer_aqgd.py +++ b/test/optimizers/test_optimizer_aqgd.py @@ -13,11 +13,16 @@ """Test of AQGD optimizer""" import unittest +<<<<<<< HEAD from test import QiskitAlgorithmsTestCase +======= +from test import QiskitAlgorithmsTestCase, slow_test +import numpy as np +from ddt import ddt, data +>>>>>>> 2245288 (Add slow_test as it's no longer part of Qiskit 1.0 (#141)) from qiskit.circuit.library import RealAmplitudes from qiskit.primitives import Estimator from qiskit.quantum_info import SparsePauliOp -from qiskit.test import slow_test from qiskit_algorithms import AlgorithmError from qiskit_algorithms.gradients import LinCombEstimatorGradient diff --git a/test/time_evolvers/test_pvqd.py b/test/time_evolvers/test_pvqd.py index 0509e8d9..740ac69f 100644 --- a/test/time_evolvers/test_pvqd.py +++ b/test/time_evolvers/test_pvqd.py @@ -1,6 +1,6 @@ # This code is part of a Qiskit project. # -# (C) Copyright IBM 2018, 2023. +# (C) Copyright IBM 2018, 2024. # # This code is licensed under the Apache License, Version 2.0. You may # obtain a copy of this license in the LICENSE.txt file in the root directory @@ -48,7 +48,7 @@ class WhatAmI(Gate): def __init__(self, angle): super().__init__(name="whatami", num_qubits=2, params=[angle]) - def inverse(self): + def inverse(self, annotated: bool = False): return WhatAmI(-self.params[0])