1414
1515import itertools as its
1616from math import sqrt
17+ from os import environ
1718from random import Random
1819
1920import cirq
2324import qiskit
2425from qiskit .circuit .random import random_circuit
2526from quimb .tensor import Tensor , TensorNetwork
26-
27- from conftest import fraction_n_tests , global_seed # Get global seed
2827from tnco .utils .circuit import commute , load , same
2928
30- rng = Random (global_seed )
29+ # Initialize RNG
30+ rng = Random (
31+ environ .get ('PYTEST_SEED' ) +
32+ environ .get ('PYTEST_XDIST_WORKER' ) if 'PYTEST_SEED' in environ else None )
33+
34+ # Fix max number of repetitions
35+ max_repeat = max (1 , float (environ .get ('PYTEST_MAX_REPEAT' , 'inf' )))
36+
37+ # Fix ratio of number of tests
38+ fraction_n_tests = max (
39+ min (float (environ .get ('PYTEST_FRACTION_N_TESTS' , '1' )), 1 ), 0 )
40+
41+
42+ def repeat (n : int ):
43+ return pytest .mark .repeat (max (min (n * fraction_n_tests , max_repeat ), 1 ))
3144
3245
33- def sample_seeds ( k , / ):
34- k = int ( max ( 1 , k * fraction_n_tests ))
35- return rng .sample ( range ( 2 ** 32 ), k = k )
46+ @ pytest . fixture
47+ def random_seed ():
48+ return rng .randrange ( 2 ** 32 )
3649
3750
38- @pytest . mark . parametrize ( 'seed' , sample_seeds ( 200 ) )
39- def test_Commute (seed , ** kwargs ):
51+ @repeat ( 20 )
52+ def test_Commute (random_seed , ** kwargs ):
4053 # Commutation using cirq
4154 def commute_ (gate_A , gate_B , * , use_matrix_commutation = True , atol = 1e-5 ):
4255 if use_matrix_commutation :
@@ -48,7 +61,7 @@ def commute_(gate_A, gate_B, *, use_matrix_commutation=True, atol=1e-5):
4861 return not frozenset (gate_A [1 ]) & frozenset (gate_B [1 ])
4962
5063 # Initialize RNG
51- rng = Random (seed )
64+ rng = Random (random_seed )
5265
5366 # Set parameters
5467 n_qubits = kwargs .get ('n_qubits' , 5 )
@@ -58,10 +71,9 @@ def commute_(gate_A, gate_B, *, use_matrix_commutation=True, atol=1e-5):
5871 circuit = tuple (
5972 map (
6073 lambda gate : (cirq .unitary (gate ), gate .qubits ),
61- cirq .testing .random_circuit (n_qubits ,
62- n_moments ,
63- op_density = 1 ,
64- random_state = seed ).all_operations ()))
74+ cirq .testing .random_circuit (
75+ n_qubits , n_moments , op_density = 1 ,
76+ random_state = random_seed ).all_operations ()))
6577
6678 # Check commutation
6779 assert all (
@@ -76,8 +88,8 @@ def commute_(gate_A, gate_B, *, use_matrix_commutation=True, atol=1e-5):
7688 zip (rng .choices (circuit , k = 200 ), rng .choices (circuit , k = 200 ))))
7789
7890
79- @pytest . mark . parametrize ( 'seed' , sample_seeds ( 200 ) )
80- def test_Same (seed , ** kwargs ):
91+ @repeat ( 20 )
92+ def test_Same (random_seed , ** kwargs ):
8193 # Same using quimb
8294 def same_ (gate_A , gate_B , atol = 1e-5 ):
8395 gate_A = Tensor (
@@ -92,7 +104,7 @@ def same_(gate_A, gate_B, atol=1e-5):
92104 gate_A .data , gate_B .transpose_like (gate_A ).data , atol = 1e-5 )
93105
94106 # Initialize RNG
95- rng = Random (seed )
107+ rng = Random (random_seed )
96108
97109 # Set parameters
98110 n_qubits = kwargs .get ('n_qubits' , 5 )
@@ -102,10 +114,9 @@ def same_(gate_A, gate_B, atol=1e-5):
102114 circuit = tuple (
103115 map (
104116 lambda gate : (cirq .unitary (gate ), gate .qubits ),
105- cirq .testing .random_circuit (n_qubits ,
106- n_moments ,
107- op_density = 1 ,
108- random_state = seed ).all_operations ()))
117+ cirq .testing .random_circuit (
118+ n_qubits , n_moments , op_density = 1 ,
119+ random_state = random_seed ).all_operations ()))
109120
110121 # Check same
111122 assert all (
@@ -116,11 +127,11 @@ def same_(gate_A, gate_B, atol=1e-5):
116127 map (lambda g : same_ (g , g ) and same (g , g ), rng .choices (circuit , k = 200 )))
117128
118129
119- @pytest . mark . parametrize ( 'seed' , sample_seeds ( 200 ) )
120- def test_LoadArbitraryInitialFinalState (seed , ** kwargs ):
130+ @repeat ( 20 )
131+ def test_LoadArbitraryInitialFinalState (random_seed , ** kwargs ):
121132 # Get rng
122- rng = Random (seed )
123- np_rng = np .random .default_rng (seed )
133+ rng = Random (random_seed )
134+ np_rng = np .random .default_rng (random_seed )
124135
125136 # Get parameters
126137 n_qubits = kwargs .get ('n_qubits' , rng .randint (5 , 10 ))
@@ -151,7 +162,7 @@ def random_qubit():
151162 circuit = cirq .testing .random_circuit (n_qubits ,
152163 n_moments ,
153164 op_density = op_density ,
154- random_state = seed )
165+ random_state = random_seed )
155166 else :
156167 circuit = cirq .testing .random_circuit (n_qubits ,
157168 n_moments ,
@@ -163,7 +174,7 @@ def random_qubit():
163174 cirq .CCZPowGate (): 3 ,
164175 cirq .ISWAP : 2
165176 },
166- random_state = seed )
177+ random_state = random_seed )
167178 circuit = map ((cirq .H ** 0.5 ).on , circuit .all_qubits ()) + circuit + map (
168179 (cirq .H ** 0.5 ).on , circuit .all_qubits ())
169180
@@ -188,7 +199,7 @@ def random_qubit():
188199 decompose_hyper_inds = decompose_hyper_inds ,
189200 fuse = fuse ,
190201 use_matrix_commutation = use_matrix_commutation ,
191- seed = seed )
202+ seed = random_seed )
192203
193204 def get_state (x ):
194205 valid_token = {
@@ -243,10 +254,10 @@ def get_state(x):
243254 np .testing .assert_allclose (ex , ts , atol = 1e-5 )
244255
245256
246- @pytest . mark . parametrize ( 'seed' , sample_seeds ( 200 ) )
247- def test_LoadUnitary (seed , ** kwargs ):
257+ @repeat ( 20 )
258+ def test_LoadUnitary (random_seed , ** kwargs ):
248259 # Get rng
249- rng = Random (seed )
260+ rng = Random (random_seed )
250261
251262 # Get parameters
252263 n_qubits = kwargs .get ('n_qubits' , rng .randint (5 , 10 ))
@@ -265,7 +276,7 @@ def test_LoadUnitary(seed, **kwargs):
265276 circuit = cirq .testing .random_circuit (n_qubits ,
266277 n_moments ,
267278 op_density = op_density ,
268- random_state = seed )
279+ random_state = random_seed )
269280 else :
270281 circuit = cirq .testing .random_circuit (n_qubits ,
271282 n_moments ,
@@ -277,7 +288,7 @@ def test_LoadUnitary(seed, **kwargs):
277288 cirq .CCZPowGate (): 3 ,
278289 cirq .ISWAP : 2
279290 },
280- random_state = seed )
291+ random_state = random_seed )
281292 circuit = map ((cirq .H ** 0.5 ).on , circuit .all_qubits ()) + circuit + map (
282293 (cirq .H ** 0.5 ).on , circuit .all_qubits ())
283294
@@ -291,7 +302,7 @@ def test_LoadUnitary(seed, **kwargs):
291302 decompose_hyper_inds = decompose_hyper_inds ,
292303 fuse = fuse ,
293304 use_matrix_commutation = use_matrix_commutation ,
294- seed = seed )
305+ seed = random_seed )
295306
296307 # Get exact unitary
297308 U = cirq .unitary (circuit )
@@ -337,8 +348,8 @@ def test_LoadUnitary(seed, **kwargs):
337348 assert not arrays and not ts_inds and not output_inds
338349
339350
340- @pytest . mark . parametrize ( 'seed' , sample_seeds ( 200 ) )
341- def test_LoadQisKit (seed ):
351+ @repeat ( 20 )
352+ def test_LoadQisKit (random_seed ):
342353 # Set number of qubits and depth of the circuit
343354 n_qubits = 6
344355 circuit_depth = 12
@@ -350,8 +361,8 @@ def test_LoadQisKit(seed):
350361 # Get a random circuit
351362 circuit = qiskit .QuantumCircuit (n_qubits )
352363 mit .consume (map (lambda i : circuit .append (sqrt_H , [i ]), range (n_qubits )))
353- circuit = circuit .compose (random_circuit ( n_qubits , circuit_depth ,
354- seed = seed ))
364+ circuit = circuit .compose (
365+ random_circuit ( n_qubits , circuit_depth , seed = random_seed ))
355366 mit .consume (map (lambda i : circuit .append (sqrt_H , [i ]), range (n_qubits )))
356367
357368 # Get unitary
0 commit comments