cirq-core 1.6.0.dev20250425004112__py3-none-any.whl → 1.6.0.dev20250429004516__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of cirq-core might be problematic. Click here for more details.

Files changed (57) hide show
  1. cirq/_version.py +1 -1
  2. cirq/_version_test.py +1 -1
  3. cirq/protocols/decompose_protocol.py +3 -2
  4. cirq/protocols/measurement_key_protocol.py +8 -7
  5. cirq/protocols/pow_protocol.py +7 -7
  6. cirq/protocols/qasm.py +5 -3
  7. cirq/protocols/resolve_parameters.py +5 -3
  8. cirq/qis/clifford_tableau.py +11 -9
  9. cirq/qis/measures.py +7 -7
  10. cirq/qis/quantum_state_representation.py +4 -5
  11. cirq/qis/states.py +19 -17
  12. cirq/sim/classical_simulator.py +15 -14
  13. cirq/sim/clifford/clifford_simulator.py +19 -17
  14. cirq/sim/clifford/clifford_tableau_simulation_state.py +7 -4
  15. cirq/sim/clifford/stabilizer_ch_form_simulation_state.py +5 -3
  16. cirq/sim/clifford/stabilizer_sampler.py +6 -4
  17. cirq/sim/clifford/stabilizer_simulation_state.py +9 -9
  18. cirq/sim/clifford/stabilizer_state_ch_form.py +6 -4
  19. cirq/sim/density_matrix_simulation_state.py +17 -18
  20. cirq/sim/density_matrix_simulator.py +21 -19
  21. cirq/sim/density_matrix_utils.py +4 -2
  22. cirq/sim/mux.py +25 -23
  23. cirq/sim/simulation_product_state.py +12 -12
  24. cirq/sim/simulation_product_state_test.py +3 -3
  25. cirq/sim/simulation_state.py +23 -19
  26. cirq/sim/simulation_state_base.py +16 -12
  27. cirq/sim/simulation_state_test.py +1 -1
  28. cirq/sim/simulator.py +71 -72
  29. cirq/sim/simulator_base.py +22 -23
  30. cirq/sim/simulator_base_test.py +12 -9
  31. cirq/sim/simulator_test.py +12 -8
  32. cirq/sim/sparse_simulator.py +13 -11
  33. cirq/sim/state_vector.py +9 -6
  34. cirq/sim/state_vector_simulation_state.py +20 -20
  35. cirq/sim/state_vector_simulator.py +13 -10
  36. cirq/study/flatten_expressions.py +8 -5
  37. cirq/study/resolver.py +12 -9
  38. cirq/study/result.py +6 -3
  39. cirq/study/sweeps.py +17 -14
  40. cirq/testing/consistent_act_on_test.py +2 -2
  41. cirq/testing/consistent_controlled_gate_op_test.py +10 -6
  42. cirq/testing/lin_alg_utils.py +8 -7
  43. cirq/testing/random_circuit.py +17 -16
  44. cirq/testing/routing_devices.py +4 -1
  45. cirq/testing/sample_circuits.py +4 -1
  46. cirq/transformers/align.py +6 -4
  47. cirq/transformers/analytical_decompositions/clifford_decomposition.py +9 -7
  48. cirq/transformers/analytical_decompositions/controlled_gate_decomposition.py +15 -13
  49. cirq/transformers/analytical_decompositions/cphase_to_fsim.py +7 -5
  50. cirq/transformers/analytical_decompositions/quantum_shannon_decomposition.py +10 -8
  51. cirq/transformers/analytical_decompositions/single_to_two_qubit_isometry.py +6 -3
  52. cirq/transformers/analytical_decompositions/two_qubit_state_preparation.py +8 -10
  53. {cirq_core-1.6.0.dev20250425004112.dist-info → cirq_core-1.6.0.dev20250429004516.dist-info}/METADATA +1 -1
  54. {cirq_core-1.6.0.dev20250425004112.dist-info → cirq_core-1.6.0.dev20250429004516.dist-info}/RECORD +57 -57
  55. {cirq_core-1.6.0.dev20250425004112.dist-info → cirq_core-1.6.0.dev20250429004516.dist-info}/WHEEL +1 -1
  56. {cirq_core-1.6.0.dev20250425004112.dist-info → cirq_core-1.6.0.dev20250429004516.dist-info}/licenses/LICENSE +0 -0
  57. {cirq_core-1.6.0.dev20250425004112.dist-info → cirq_core-1.6.0.dev20250429004516.dist-info}/top_level.txt +0 -0
@@ -14,6 +14,8 @@
14
14
 
15
15
  """A simulator that uses numpy's einsum for sparse matrix operations."""
16
16
 
17
+ from __future__ import annotations
18
+
17
19
  from typing import Any, Iterator, List, Optional, Sequence, Type, TYPE_CHECKING, Union
18
20
 
19
21
  import numpy as np
@@ -126,8 +128,8 @@ class Simulator(
126
128
  self,
127
129
  *,
128
130
  dtype: Type[np.complexfloating] = np.complex64,
129
- noise: 'cirq.NOISE_MODEL_LIKE' = None,
130
- seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None,
131
+ noise: cirq.NOISE_MODEL_LIKE = None,
132
+ seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None,
131
133
  split_untangled_states: bool = True,
132
134
  ):
133
135
  """A sparse matrix simulator.
@@ -152,9 +154,9 @@ class Simulator(
152
154
 
153
155
  def _create_partial_simulation_state(
154
156
  self,
155
- initial_state: Union['cirq.STATE_VECTOR_LIKE', 'cirq.StateVectorSimulationState'],
156
- qubits: Sequence['cirq.Qid'],
157
- classical_data: 'cirq.ClassicalDataStore',
157
+ initial_state: Union[cirq.STATE_VECTOR_LIKE, cirq.StateVectorSimulationState],
158
+ qubits: Sequence[cirq.Qid],
159
+ classical_data: cirq.ClassicalDataStore,
158
160
  ):
159
161
  """Creates the StateVectorSimulationState for a circuit.
160
162
 
@@ -183,16 +185,16 @@ class Simulator(
183
185
  )
184
186
 
185
187
  def _create_step_result(
186
- self, sim_state: 'cirq.SimulationStateBase[cirq.StateVectorSimulationState]'
188
+ self, sim_state: cirq.SimulationStateBase[cirq.StateVectorSimulationState]
187
189
  ):
188
190
  return SparseSimulatorStep(sim_state=sim_state, dtype=self._dtype)
189
191
 
190
192
  def simulate_expectation_values_sweep_iter(
191
193
  self,
192
- program: 'cirq.AbstractCircuit',
193
- observables: Union['cirq.PauliSumLike', List['cirq.PauliSumLike']],
194
- params: 'cirq.Sweepable',
195
- qubit_order: 'cirq.QubitOrderOrList' = ops.QubitOrder.DEFAULT,
194
+ program: cirq.AbstractCircuit,
195
+ observables: Union[cirq.PauliSumLike, List[cirq.PauliSumLike]],
196
+ params: cirq.Sweepable,
197
+ qubit_order: cirq.QubitOrderOrList = ops.QubitOrder.DEFAULT,
196
198
  initial_state: Any = None,
197
199
  permit_terminal_measurements: bool = False,
198
200
  ) -> Iterator[List[float]]:
@@ -222,7 +224,7 @@ class SparseSimulatorStep(
222
224
 
223
225
  def __init__(
224
226
  self,
225
- sim_state: 'cirq.SimulationStateBase[cirq.StateVectorSimulationState]',
227
+ sim_state: cirq.SimulationStateBase[cirq.StateVectorSimulationState],
226
228
  dtype: Type[np.complexfloating] = np.complex64,
227
229
  ):
228
230
  """Results of a step of the simulator.
cirq/sim/state_vector.py CHANGED
@@ -11,8 +11,11 @@
11
11
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
+
14
15
  """Helpers for handling quantum state vectors."""
15
16
 
17
+ from __future__ import annotations
18
+
16
19
  import abc
17
20
  from typing import List, Mapping, Optional, Sequence, Tuple, TYPE_CHECKING
18
21
 
@@ -31,7 +34,7 @@ if TYPE_CHECKING:
31
34
  class StateVectorMixin:
32
35
  """A mixin that provide methods for objects that have a state vector."""
33
36
 
34
- def __init__(self, qubit_map: Optional[Mapping['cirq.Qid', int]] = None, *args, **kwargs):
37
+ def __init__(self, qubit_map: Optional[Mapping[cirq.Qid, int]] = None, *args, **kwargs):
35
38
  """Inits StateVectorMixin.
36
39
 
37
40
  Args:
@@ -47,7 +50,7 @@ class StateVectorMixin:
47
50
  self._qid_shape = None if qubit_map is None else qid_shape
48
51
 
49
52
  @property
50
- def qubit_map(self) -> Mapping['cirq.Qid', int]:
53
+ def qubit_map(self) -> Mapping[cirq.Qid, int]:
51
54
  return self._qubit_map
52
55
 
53
56
  def _qid_shape_(self) -> Tuple[int, ...]:
@@ -102,7 +105,7 @@ class StateVectorMixin:
102
105
  and non-zero floats of the specified accuracy."""
103
106
  return qis.dirac_notation(self.state_vector(), decimals, qid_shape=self._qid_shape)
104
107
 
105
- def density_matrix_of(self, qubits: Optional[List['cirq.Qid']] = None) -> np.ndarray:
108
+ def density_matrix_of(self, qubits: Optional[List[cirq.Qid]] = None) -> np.ndarray:
106
109
  r"""Returns the density matrix of the state.
107
110
 
108
111
  Calculate the density matrix for the system on the qubits provided.
@@ -141,7 +144,7 @@ class StateVectorMixin:
141
144
  qid_shape=self._qid_shape,
142
145
  )
143
146
 
144
- def bloch_vector_of(self, qubit: 'cirq.Qid') -> np.ndarray:
147
+ def bloch_vector_of(self, qubit: cirq.Qid) -> np.ndarray:
145
148
  """Returns the bloch vector of a qubit in the state.
146
149
 
147
150
  Calculates the bloch vector of the given qubit
@@ -171,7 +174,7 @@ def sample_state_vector(
171
174
  *, # Force keyword args
172
175
  qid_shape: Optional[Tuple[int, ...]] = None,
173
176
  repetitions: int = 1,
174
- seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None,
177
+ seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None,
175
178
  ) -> np.ndarray:
176
179
  """Samples repeatedly from measurements in the computational basis.
177
180
 
@@ -236,7 +239,7 @@ def measure_state_vector(
236
239
  *, # Force keyword args
237
240
  qid_shape: Optional[Tuple[int, ...]] = None,
238
241
  out: Optional[np.ndarray] = None,
239
- seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None,
242
+ seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None,
240
243
  ) -> Tuple[List[int], np.ndarray]:
241
244
  """Performs a measurement of the state in the computational basis.
242
245
 
@@ -13,6 +13,9 @@
13
13
  # limitations under the License.
14
14
 
15
15
  """Objects and methods for acting efficiently on a state vector."""
16
+
17
+ from __future__ import annotations
18
+
16
19
  from typing import Any, Callable, List, Optional, Sequence, Tuple, Type, TYPE_CHECKING, Union
17
20
 
18
21
  import numpy as np
@@ -50,7 +53,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
50
53
  def create(
51
54
  cls,
52
55
  *,
53
- initial_state: Union[np.ndarray, 'cirq.STATE_VECTOR_LIKE'] = 0,
56
+ initial_state: Union[np.ndarray, cirq.STATE_VECTOR_LIKE] = 0,
54
57
  qid_shape: Optional[Tuple[int, ...]] = None,
55
58
  dtype: Optional[Type[np.complexfloating]] = None,
56
59
  buffer: Optional[np.ndarray] = None,
@@ -85,7 +88,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
85
88
  state_vector = state_vector.astype(dtype, copy=False)
86
89
  return cls(state_vector, buffer)
87
90
 
88
- def copy(self, deep_copy_buffers: bool = True) -> '_BufferedStateVector':
91
+ def copy(self, deep_copy_buffers: bool = True) -> _BufferedStateVector:
89
92
  """Copies the object.
90
93
 
91
94
  Args:
@@ -98,7 +101,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
98
101
  buffer=self._buffer.copy() if deep_copy_buffers else self._buffer,
99
102
  )
100
103
 
101
- def kron(self, other: '_BufferedStateVector') -> '_BufferedStateVector':
104
+ def kron(self, other: _BufferedStateVector) -> _BufferedStateVector:
102
105
  """Creates the Kronecker product with the other state vector.
103
106
 
104
107
  Args:
@@ -113,7 +116,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
113
116
 
114
117
  def factor(
115
118
  self, axes: Sequence[int], *, validate=True, atol=1e-07
116
- ) -> Tuple['_BufferedStateVector', '_BufferedStateVector']:
119
+ ) -> Tuple[_BufferedStateVector, _BufferedStateVector]:
117
120
  """Factors a state vector into two independent state vectors.
118
121
 
119
122
  This function should only be called on state vectors that are known to be separable, such
@@ -143,7 +146,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
143
146
  )
144
147
  return extracted, remainder
145
148
 
146
- def reindex(self, axes: Sequence[int]) -> '_BufferedStateVector':
149
+ def reindex(self, axes: Sequence[int]) -> _BufferedStateVector:
147
150
  """Transposes the axes of a state vector to a specified order.
148
151
 
149
152
  Args:
@@ -253,7 +256,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
253
256
  return index
254
257
 
255
258
  def measure(
256
- self, axes: Sequence[int], seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None
259
+ self, axes: Sequence[int], seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None
257
260
  ) -> List[int]:
258
261
  """Measures the state vector.
259
262
 
@@ -269,10 +272,7 @@ class _BufferedStateVector(qis.QuantumStateRepresentation):
269
272
  return bits
270
273
 
271
274
  def sample(
272
- self,
273
- axes: Sequence[int],
274
- repetitions: int = 1,
275
- seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None,
275
+ self, axes: Sequence[int], repetitions: int = 1, seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None
276
276
  ) -> np.ndarray:
277
277
  """Samples the state vector.
278
278
 
@@ -322,10 +322,10 @@ class StateVectorSimulationState(SimulationState[_BufferedStateVector]):
322
322
  *,
323
323
  available_buffer: Optional[np.ndarray] = None,
324
324
  prng: Optional[np.random.RandomState] = None,
325
- qubits: Optional[Sequence['cirq.Qid']] = None,
326
- initial_state: Union[np.ndarray, 'cirq.STATE_VECTOR_LIKE'] = 0,
325
+ qubits: Optional[Sequence[cirq.Qid]] = None,
326
+ initial_state: Union[np.ndarray, cirq.STATE_VECTOR_LIKE] = 0,
327
327
  dtype: Type[np.complexfloating] = np.complex64,
328
- classical_data: Optional['cirq.ClassicalDataStore'] = None,
328
+ classical_data: Optional[cirq.ClassicalDataStore] = None,
329
329
  ):
330
330
  """Inits StateVectorSimulationState.
331
331
 
@@ -356,7 +356,7 @@ class StateVectorSimulationState(SimulationState[_BufferedStateVector]):
356
356
  )
357
357
  super().__init__(state=state, prng=prng, qubits=qubits, classical_data=classical_data)
358
358
 
359
- def add_qubits(self, qubits: Sequence['cirq.Qid']):
359
+ def add_qubits(self, qubits: Sequence[cirq.Qid]):
360
360
  ret = super().add_qubits(qubits)
361
361
  return (
362
362
  self.kronecker_product(type(self)(qubits=qubits), inplace=True)
@@ -364,7 +364,7 @@ class StateVectorSimulationState(SimulationState[_BufferedStateVector]):
364
364
  else ret
365
365
  )
366
366
 
367
- def remove_qubits(self, qubits: Sequence['cirq.Qid']):
367
+ def remove_qubits(self, qubits: Sequence[cirq.Qid]):
368
368
  ret = super().remove_qubits(qubits)
369
369
  if ret is not NotImplemented:
370
370
  return ret
@@ -373,9 +373,9 @@ class StateVectorSimulationState(SimulationState[_BufferedStateVector]):
373
373
  return remainder
374
374
 
375
375
  def _act_on_fallback_(
376
- self, action: Any, qubits: Sequence['cirq.Qid'], allow_decompose: bool = True
376
+ self, action: Any, qubits: Sequence[cirq.Qid], allow_decompose: bool = True
377
377
  ) -> bool:
378
- strats: List[Callable[[Any, Any, Sequence['cirq.Qid']], bool]] = [
378
+ strats: List[Callable[[Any, Any, Sequence[cirq.Qid]], bool]] = [
379
379
  _strat_act_on_state_vector_from_apply_unitary,
380
380
  _strat_act_on_state_vector_from_mixture,
381
381
  _strat_act_on_state_vector_from_channel,
@@ -415,7 +415,7 @@ class StateVectorSimulationState(SimulationState[_BufferedStateVector]):
415
415
 
416
416
 
417
417
  def _strat_act_on_state_vector_from_apply_unitary(
418
- action: Any, args: 'cirq.StateVectorSimulationState', qubits: Sequence['cirq.Qid']
418
+ action: Any, args: cirq.StateVectorSimulationState, qubits: Sequence[cirq.Qid]
419
419
  ) -> bool:
420
420
  if not args._state.apply_unitary(action, args.get_axes(qubits)):
421
421
  return NotImplemented
@@ -423,7 +423,7 @@ def _strat_act_on_state_vector_from_apply_unitary(
423
423
 
424
424
 
425
425
  def _strat_act_on_state_vector_from_mixture(
426
- action: Any, args: 'cirq.StateVectorSimulationState', qubits: Sequence['cirq.Qid']
426
+ action: Any, args: cirq.StateVectorSimulationState, qubits: Sequence[cirq.Qid]
427
427
  ) -> bool:
428
428
  index = args._state.apply_mixture(action, args.get_axes(qubits), args.prng)
429
429
  if index is None:
@@ -435,7 +435,7 @@ def _strat_act_on_state_vector_from_mixture(
435
435
 
436
436
 
437
437
  def _strat_act_on_state_vector_from_channel(
438
- action: Any, args: 'cirq.StateVectorSimulationState', qubits: Sequence['cirq.Qid']
438
+ action: Any, args: cirq.StateVectorSimulationState, qubits: Sequence[cirq.Qid]
439
439
  ) -> bool:
440
440
  index = args._state.apply_channel(action, args.get_axes(qubits), args.prng)
441
441
  if index is None:
@@ -11,8 +11,11 @@
11
11
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
+
14
15
  """Abstract classes for simulations which keep track of state vector."""
15
16
 
17
+ from __future__ import annotations
18
+
16
19
  import abc
17
20
  import warnings
18
21
  from functools import cached_property
@@ -48,8 +51,8 @@ class SimulatesIntermediateStateVector(
48
51
  self,
49
52
  *,
50
53
  dtype: Type[np.complexfloating] = np.complex64,
51
- noise: 'cirq.NOISE_MODEL_LIKE' = None,
52
- seed: 'cirq.RANDOM_STATE_OR_SEED_LIKE' = None,
54
+ noise: cirq.NOISE_MODEL_LIKE = None,
55
+ seed: cirq.RANDOM_STATE_OR_SEED_LIKE = None,
53
56
  split_untangled_states: bool = False,
54
57
  ):
55
58
  super().__init__(
@@ -58,20 +61,20 @@ class SimulatesIntermediateStateVector(
58
61
 
59
62
  def _create_simulator_trial_result(
60
63
  self,
61
- params: 'cirq.ParamResolver',
64
+ params: cirq.ParamResolver,
62
65
  measurements: Dict[str, np.ndarray],
63
- final_simulator_state: 'cirq.SimulationStateBase[cirq.StateVectorSimulationState]',
64
- ) -> 'cirq.StateVectorTrialResult':
66
+ final_simulator_state: cirq.SimulationStateBase[cirq.StateVectorSimulationState],
67
+ ) -> cirq.StateVectorTrialResult:
65
68
  return StateVectorTrialResult(
66
69
  params=params, measurements=measurements, final_simulator_state=final_simulator_state
67
70
  )
68
71
 
69
72
  def compute_amplitudes_sweep_iter(
70
73
  self,
71
- program: 'cirq.AbstractCircuit',
74
+ program: cirq.AbstractCircuit,
72
75
  bitstrings: Sequence[int],
73
- params: 'cirq.Sweepable',
74
- qubit_order: 'cirq.QubitOrderOrList' = ops.QubitOrder.DEFAULT,
76
+ params: cirq.Sweepable,
77
+ qubit_order: cirq.QubitOrderOrList = ops.QubitOrder.DEFAULT,
75
78
  ) -> Iterator[Sequence[complex]]:
76
79
  if isinstance(bitstrings, np.ndarray) and len(bitstrings.shape) > 1:
77
80
  raise ValueError(
@@ -112,9 +115,9 @@ class StateVectorTrialResult(
112
115
 
113
116
  def __init__(
114
117
  self,
115
- params: 'cirq.ParamResolver',
118
+ params: cirq.ParamResolver,
116
119
  measurements: Dict[str, np.ndarray],
117
- final_simulator_state: 'cirq.SimulationStateBase[cirq.StateVectorSimulationState]',
120
+ final_simulator_state: cirq.SimulationStateBase[cirq.StateVectorSimulationState],
118
121
  ) -> None:
119
122
  super().__init__(
120
123
  params=params,
@@ -11,8 +11,11 @@
11
11
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
+
14
15
  """Resolves symbolic expressions to unique symbols."""
15
16
 
17
+ from __future__ import annotations
18
+
16
19
  import numbers
17
20
  from typing import Any, Callable, List, Optional, Tuple, TYPE_CHECKING, Union
18
21
 
@@ -25,7 +28,7 @@ if TYPE_CHECKING:
25
28
  import cirq
26
29
 
27
30
 
28
- def flatten(val: Any) -> Tuple[Any, 'ExpressionMap']:
31
+ def flatten(val: Any) -> Tuple[Any, ExpressionMap]:
29
32
  """Creates a copy of `val` with any symbols or expressions replaced with
30
33
  new symbols. `val` can be a `Circuit`, `Gate`, `Operation`, or other
31
34
  type.
@@ -250,8 +253,8 @@ class _ParamFlattener(resolver.ParamResolver):
250
253
  return symbol
251
254
 
252
255
  def value_of(
253
- self, value: Union['cirq.TParamKey', 'cirq.TParamValComplex'], recursive: bool = False
254
- ) -> 'cirq.TParamValComplex':
256
+ self, value: Union[cirq.TParamKey, cirq.TParamValComplex], recursive: bool = False
257
+ ) -> cirq.TParamValComplex:
255
258
  """Resolves a symbol or expression to a new symbol unique to that value.
256
259
 
257
260
  - If value is a float, returns it.
@@ -380,8 +383,8 @@ class ExpressionMap(dict):
380
383
 
381
384
 
382
385
  def _ensure_not_str(
383
- param: Union[sympy.Expr, 'cirq.TParamValComplex', str],
384
- ) -> Union[sympy.Expr, 'cirq.TParamValComplex']:
386
+ param: Union[sympy.Expr, cirq.TParamValComplex, str],
387
+ ) -> Union[sympy.Expr, cirq.TParamValComplex]:
385
388
  if isinstance(param, str):
386
389
  return sympy.Symbol(param)
387
390
  return param
cirq/study/resolver.py CHANGED
@@ -13,6 +13,9 @@
13
13
  # limitations under the License.
14
14
 
15
15
  """Resolves ParameterValues to assigned values."""
16
+
17
+ from __future__ import annotations
18
+
16
19
  import numbers
17
20
  from typing import Any, cast, Dict, Iterator, Mapping, Optional, TYPE_CHECKING, Union
18
21
 
@@ -61,12 +64,12 @@ class ParamResolver:
61
64
  TypeError if formulas are passed as keys.
62
65
  """
63
66
 
64
- def __new__(cls, param_dict: 'cirq.ParamResolverOrSimilarType' = None):
67
+ def __new__(cls, param_dict: cirq.ParamResolverOrSimilarType = None):
65
68
  if isinstance(param_dict, ParamResolver):
66
69
  return param_dict
67
70
  return super().__new__(cls)
68
71
 
69
- def __init__(self, param_dict: 'cirq.ParamResolverOrSimilarType' = None) -> None:
72
+ def __init__(self, param_dict: cirq.ParamResolverOrSimilarType = None) -> None:
70
73
  if hasattr(self, 'param_dict'):
71
74
  return # Already initialized. Got wrapped as part of the __new__.
72
75
 
@@ -82,8 +85,8 @@ class ParamResolver:
82
85
  return self._param_dict
83
86
 
84
87
  def value_of(
85
- self, value: Union['cirq.TParamKey', 'cirq.TParamValComplex'], recursive: bool = True
86
- ) -> 'cirq.TParamValComplex':
88
+ self, value: Union[cirq.TParamKey, cirq.TParamValComplex], recursive: bool = True
89
+ ) -> cirq.TParamValComplex:
87
90
  """Attempt to resolve a parameter to its assigned value.
88
91
 
89
92
  Scalars are returned without modification. Strings are resolved via
@@ -193,7 +196,7 @@ class ParamResolver:
193
196
 
194
197
  return self._value_of_recursive(value)
195
198
 
196
- def _value_of_recursive(self, value: 'cirq.TParamKey') -> 'cirq.TParamValComplex':
199
+ def _value_of_recursive(self, value: cirq.TParamKey) -> cirq.TParamValComplex:
197
200
  # Recursive parameter resolution. We can safely assume that value is a
198
201
  # single symbol, since combinations are handled earlier in the method.
199
202
  if value in self._deep_eval_map:
@@ -213,8 +216,8 @@ class ParamResolver:
213
216
  self._deep_eval_map[value] = self.value_of(v, recursive=True)
214
217
  return self._deep_eval_map[value]
215
218
 
216
- def _resolve_parameters_(self, resolver: 'ParamResolver', recursive: bool) -> 'ParamResolver':
217
- new_dict: Dict['cirq.TParamKey', Union[float, str, sympy.Symbol, sympy.Expr]] = {
219
+ def _resolve_parameters_(self, resolver: ParamResolver, recursive: bool) -> ParamResolver:
220
+ new_dict: Dict[cirq.TParamKey, Union[float, str, sympy.Symbol, sympy.Expr]] = {
218
221
  k: k for k in resolver
219
222
  }
220
223
  new_dict.update({k: self.value_of(k, recursive) for k in self})
@@ -232,8 +235,8 @@ class ParamResolver:
232
235
  return bool(self._param_dict)
233
236
 
234
237
  def __getitem__(
235
- self, key: Union['cirq.TParamKey', 'cirq.TParamValComplex']
236
- ) -> 'cirq.TParamValComplex':
238
+ self, key: Union[cirq.TParamKey, cirq.TParamValComplex]
239
+ ) -> cirq.TParamValComplex:
237
240
  return self.value_of(key)
238
241
 
239
242
  def __hash__(self) -> int:
cirq/study/result.py CHANGED
@@ -11,8 +11,11 @@
11
11
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
+
14
15
  """Defines trial results."""
15
16
 
17
+ from __future__ import annotations
18
+
16
19
  import abc
17
20
  import collections
18
21
  import io
@@ -99,7 +102,7 @@ class Result(abc.ABC):
99
102
 
100
103
  @property
101
104
  @abc.abstractmethod
102
- def params(self) -> 'cirq.ParamResolver':
105
+ def params(self) -> cirq.ParamResolver:
103
106
  """A ParamResolver of settings used for this result."""
104
107
 
105
108
  @property
@@ -275,7 +278,7 @@ class Result(abc.ABC):
275
278
  and self.params == other.params
276
279
  )
277
280
 
278
- def __add__(self, other: 'cirq.Result') -> 'cirq.Result':
281
+ def __add__(self, other: cirq.Result) -> cirq.Result:
279
282
  if not isinstance(other, Result):
280
283
  return NotImplemented
281
284
  if self.params != other.params:
@@ -341,7 +344,7 @@ class ResultDict(Result):
341
344
  self._data: Optional[pd.DataFrame] = None
342
345
 
343
346
  @property
344
- def params(self) -> 'cirq.ParamResolver':
347
+ def params(self) -> cirq.ParamResolver:
345
348
  return self._params
346
349
 
347
350
  @property
cirq/study/sweeps.py CHANGED
@@ -11,6 +11,9 @@
11
11
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
+
15
+ from __future__ import annotations
16
+
14
17
  import abc
15
18
  import collections
16
19
  import itertools
@@ -71,7 +74,7 @@ class Sweep(metaclass=abc.ABCMeta):
71
74
  see the Product and Zip documentation.
72
75
  """
73
76
 
74
- def __mul__(self, other: 'Sweep') -> 'Sweep':
77
+ def __mul__(self, other: Sweep) -> Sweep:
75
78
  factors: List[Sweep] = []
76
79
  if isinstance(self, Product):
77
80
  factors.extend(self.factors)
@@ -85,7 +88,7 @@ class Sweep(metaclass=abc.ABCMeta):
85
88
  raise TypeError(f'cannot multiply sweep and {type(other)}')
86
89
  return Product(*factors)
87
90
 
88
- def __add__(self, other: 'Sweep') -> 'Sweep':
91
+ def __add__(self, other: Sweep) -> Sweep:
89
92
  sweeps: List[Sweep] = []
90
93
  if isinstance(self, Zip):
91
94
  sweeps.extend(self.sweeps)
@@ -108,7 +111,7 @@ class Sweep(metaclass=abc.ABCMeta):
108
111
 
109
112
  @property
110
113
  @abc.abstractmethod
111
- def keys(self) -> List['cirq.TParamKey']:
114
+ def keys(self) -> List[cirq.TParamKey]:
112
115
  """The keys for the all of the sympy.Symbols that are resolved."""
113
116
 
114
117
  @abc.abstractmethod
@@ -125,10 +128,10 @@ class Sweep(metaclass=abc.ABCMeta):
125
128
  pass
126
129
 
127
130
  @overload
128
- def __getitem__(self, val: slice) -> 'Sweep':
131
+ def __getitem__(self, val: slice) -> Sweep:
129
132
  pass
130
133
 
131
- def __getitem__(self, val: Union[int, slice]) -> Union[resolver.ParamResolver, 'Sweep']:
134
+ def __getitem__(self, val: Union[int, slice]) -> Union[resolver.ParamResolver, Sweep]:
132
135
  n = len(self)
133
136
  if isinstance(val, int):
134
137
  if val < -n or val >= n:
@@ -186,7 +189,7 @@ class _Unit(Sweep):
186
189
  return True
187
190
 
188
191
  @property
189
- def keys(self) -> List['cirq.TParamKey']:
192
+ def keys(self) -> List[cirq.TParamKey]:
190
193
  return []
191
194
 
192
195
  def __len__(self) -> int:
@@ -233,7 +236,7 @@ class Product(Sweep):
233
236
  return hash(tuple(self.factors))
234
237
 
235
238
  @property
236
- def keys(self) -> List['cirq.TParamKey']:
239
+ def keys(self) -> List[cirq.TParamKey]:
237
240
  return sum((factor.keys for factor in self.factors), [])
238
241
 
239
242
  def __len__(self) -> int:
@@ -308,7 +311,7 @@ class Concat(Sweep):
308
311
  return hash(tuple(self.sweeps))
309
312
 
310
313
  @property
311
- def keys(self) -> List['cirq.TParamKey']:
314
+ def keys(self) -> List[cirq.TParamKey]:
312
315
  return self.sweeps[0].keys
313
316
 
314
317
  def __len__(self) -> int:
@@ -361,7 +364,7 @@ class Zip(Sweep):
361
364
  return hash(tuple(self.sweeps))
362
365
 
363
366
  @property
364
- def keys(self) -> List['cirq.TParamKey']:
367
+ def keys(self) -> List[cirq.TParamKey]:
365
368
  return sum((sweep.keys for sweep in self.sweeps), [])
366
369
 
367
370
  def __len__(self) -> int:
@@ -449,7 +452,7 @@ class ZipLongest(Zip):
449
452
  class SingleSweep(Sweep):
450
453
  """A simple sweep over one parameter with values from an iterator."""
451
454
 
452
- def __init__(self, key: 'cirq.TParamKey') -> None:
455
+ def __init__(self, key: cirq.TParamKey) -> None:
453
456
  if isinstance(key, sympy.Symbol):
454
457
  key = str(key)
455
458
  self.key = key
@@ -467,7 +470,7 @@ class SingleSweep(Sweep):
467
470
  pass
468
471
 
469
472
  @property
470
- def keys(self) -> List['cirq.TParamKey']:
473
+ def keys(self) -> List[cirq.TParamKey]:
471
474
  return [self.key]
472
475
 
473
476
  def param_tuples(self) -> Iterator[Params]:
@@ -483,7 +486,7 @@ class Points(SingleSweep):
483
486
  """A simple sweep with explicitly supplied values."""
484
487
 
485
488
  def __init__(
486
- self, key: 'cirq.TParamKey', points: Sequence[float], metadata: Optional[Any] = None
489
+ self, key: cirq.TParamKey, points: Sequence[float], metadata: Optional[Any] = None
487
490
  ) -> None:
488
491
  """Creates a sweep on a variable with supplied values.
489
492
 
@@ -524,7 +527,7 @@ class Linspace(SingleSweep):
524
527
 
525
528
  def __init__(
526
529
  self,
527
- key: 'cirq.TParamKey',
530
+ key: cirq.TParamKey,
528
531
  start: float,
529
532
  stop: float,
530
533
  length: int,
@@ -607,7 +610,7 @@ class ListSweep(Sweep):
607
610
  return not self == other
608
611
 
609
612
  @property
610
- def keys(self) -> List['cirq.TParamKey']:
613
+ def keys(self) -> List[cirq.TParamKey]:
611
614
  if not self.resolver_list:
612
615
  return []
613
616
  return list(map(str, self.resolver_list[0].param_dict))
@@ -24,7 +24,7 @@ class GoodGate(cirq.testing.SingleQubitGate):
24
24
  def _unitary_(self):
25
25
  return np.array([[0, 1], [1, 0]])
26
26
 
27
- def _act_on_(self, sim_state: 'cirq.SimulationStateBase', qubits: Sequence['cirq.Qid']):
27
+ def _act_on_(self, sim_state: cirq.SimulationStateBase, qubits: Sequence[cirq.Qid]):
28
28
  if isinstance(sim_state, cirq.CliffordTableauSimulationState):
29
29
  tableau = sim_state.tableau
30
30
  q = sim_state.qubit_map[qubits[0]]
@@ -37,7 +37,7 @@ class BadGate(cirq.testing.SingleQubitGate):
37
37
  def _unitary_(self):
38
38
  return np.array([[0, 1j], [1, 0]])
39
39
 
40
- def _act_on_(self, sim_state: 'cirq.SimulationStateBase', qubits: Sequence['cirq.Qid']):
40
+ def _act_on_(self, sim_state: cirq.SimulationStateBase, qubits: Sequence[cirq.Qid]):
41
41
  if isinstance(sim_state, cirq.CliffordTableauSimulationState):
42
42
  tableau = sim_state.tableau
43
43
  q = sim_state.qubit_map[qubits[0]]
@@ -12,13 +12,17 @@
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
14
 
15
- from typing import Collection, List, Optional, Sequence, Tuple, Union
15
+ from __future__ import annotations
16
+
17
+ from typing import Collection, List, Optional, Sequence, Tuple, TYPE_CHECKING, Union
16
18
 
17
19
  import numpy as np
18
20
  import pytest
19
21
 
20
22
  import cirq
21
- from cirq.ops import control_values as cv
23
+
24
+ if TYPE_CHECKING:
25
+ from cirq.ops import control_values as cv
22
26
 
23
27
 
24
28
  class GoodGate(cirq.EigenGate, cirq.testing.SingleQubitGate):
@@ -29,11 +33,11 @@ class GoodGate(cirq.EigenGate, cirq.testing.SingleQubitGate):
29
33
  class BadGateOperation(cirq.GateOperation):
30
34
  def controlled_by(
31
35
  self,
32
- *control_qubits: 'cirq.Qid',
36
+ *control_qubits: cirq.Qid,
33
37
  control_values: Optional[
34
38
  Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
35
39
  ] = None,
36
- ) -> 'cirq.Operation':
40
+ ) -> cirq.Operation:
37
41
  return cirq.ControlledOperation(control_qubits, self, control_values)
38
42
 
39
43
 
@@ -41,7 +45,7 @@ class BadGate(cirq.EigenGate, cirq.testing.SingleQubitGate):
41
45
  def _eigen_components(self) -> List[Tuple[float, np.ndarray]]:
42
46
  return [(0, np.diag([1, 0])), (1, np.diag([0, 1]))]
43
47
 
44
- def on(self, *qubits: 'cirq.Qid') -> 'cirq.Operation':
48
+ def on(self, *qubits: cirq.Qid) -> cirq.Operation:
45
49
  return BadGateOperation(self, list(qubits))
46
50
 
47
51
  def controlled(
@@ -51,7 +55,7 @@ class BadGate(cirq.EigenGate, cirq.testing.SingleQubitGate):
51
55
  Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
52
56
  ] = None,
53
57
  control_qid_shape: Optional[Tuple[int, ...]] = None,
54
- ) -> 'cirq.Gate':
58
+ ) -> cirq.Gate:
55
59
  ret = super().controlled(num_controls, control_values, control_qid_shape)
56
60
  if num_controls == 1 and control_values is None:
57
61
  return cirq.CZPowGate(exponent=self._exponent, global_shift=self._global_shift)