/
testContinuousGates.py
125 lines (94 loc) · 5.03 KB
/
testContinuousGates.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
import logging
mpl_logger = logging.getLogger('matplotlib')
mpl_logger.setLevel(logging.WARNING)
import unittest
import pygsti
import numpy as np
from pygsti.construction import std1Q_XYI
from pygsti.construction import std2Q_XYICNOT
from pygsti.objects import Label as L
import pygsti.construction as pc
import sys, os, warnings
from ..testutils import BaseTestCase, compare_files, temp_files
#Note: these are the same sample factory classes used elsewhere in the unit tests - TODO: consolidate
class XRotationOp(pygsti.obj.DenseOperator):
def __init__(self, target_angle, initial_params=(0,0)):
#initialize with no noise
self.target_angle = target_angle
self.from_vector(np.array(initial_params,'d'))
super(XRotationOp,self).__init__(self.base, "densitymx") # this is *super*-operator, so "densitymx"
def num_params(self):
return 2 # we have two parameters
def to_vector(self):
return np.array([self.depol_amt, self.over_rotation],'d') #our parameter vector
def from_vector(self,v):
#initialize from parameter vector v
self.depol_amt = v[0]
self.over_rotation = v[1]
theta = (self.target_angle + self.over_rotation)/2
a = 1.0-self.depol_amt
b = a*2*np.cos(theta)*np.sin(theta)
c = a*(np.cos(theta)**2 - np.sin(theta)**2)
# .base is a member of DenseOperator and is a numpy array that is
# the dense Pauli transfer matrix of this operator
self.base = np.array([[1, 0, 0, 0],
[0, a, 0, 0],
[0, 0, c, -b],
[0, 0, b, c]],'d')
class ParamXRotationOpFactory(pygsti.obj.OpFactory):
def __init__(self):
dim = 4 # 1-qubit
self.params = np.array([0,0],'d') #initialize with no noise
pygsti.obj.OpFactory.__init__(self, dim, "densitymx")
def create_object(self, args=None, sslbls=None):
assert(sslbls is None) # we don't use these, and they're only non-None when we're expected to use them
assert(len(args) == 1)
return XRotationOp( float(args[0]) ) #no need to set parameters of returned op - done by base class
def num_params(self):
return len(self.params) # we have two parameters
def to_vector(self):
return self.params #our parameter vector
def from_vector(self,v):
self.params[:] = v
class ContinuousGatesTestCase(BaseTestCase):
def setUp(self):
super(ContinuousGatesTestCase, self).setUp()
def test_continuous_gates_gst(self):
nQubits = 1
#Create some sequences:
smq1Q_XYI = pygsti.construction.stdmodule_to_smqmodule(std1Q_XYI)
maxLens = [1]
seqStructs = pygsti.construction.make_lsgst_structs(
smq1Q_XYI.target_model(), smq1Q_XYI.prepStrs, smq1Q_XYI.effectStrs, smq1Q_XYI.germs, maxLens)
#Add random X-rotations via label arguments
np.random.seed(1234)
def sub_Gxrots(circuit):
ret = circuit.replace_layer( ('Gx',0), ('Gxrot',0,';',np.pi/2 + 0.02*(np.random.random()-0.5)) )
return ret
ss0 = seqStructs[0].copy()
ss1 = ss0.process_circuits(sub_Gxrots)
allStrs = pygsti.tools.remove_duplicates(ss0.allstrs + ss1.allstrs)
print(len(allStrs),"sequences ")
self.assertEqual(len(allStrs), 167)
#Generate some data for these sequences (simulates an implicit model with factory)
mdl_datagen = pygsti.obj.LocalNoiseModel.build_from_parameterization(
nQubits, ('Gi','Gx','Gy'), parameterization="H+S")
mdl_datagen.factories['layers'][('Gxrot', 0)] = ParamXRotationOpFactory()
print(mdl_datagen.num_params(), "model params")
self.assertEqual(mdl_datagen.num_params(), 32)
np.random.seed(4567)
datagen_vec = 0.001 * np.random.random(mdl_datagen.num_params())
mdl_datagen.from_vector(datagen_vec)
ds = pygsti.construction.generate_fake_data(mdl_datagen, allStrs, 1000, seed=1234)
#Run GST
mdl = pygsti.obj.LocalNoiseModel.build_from_parameterization(
nQubits, ('Gi','Gx','Gy'), parameterization="H+S")
mdl.factories['layers'][('Gxrot', 0)] = ParamXRotationOpFactory()
mdl.set_simtype('map') # must use map calcs with factories (at least for now, since matrix eval trees don't know about all possible gates?)
#mdl.from_vector( datagen_vec ) # DEBUG - used to see at where optimization should get us...
results = pygsti.do_long_sequence_gst_base(ds, mdl, [allStrs], gaugeOptParams=False, verbosity=3)
_, nSigma, pval = pygsti.two_delta_logl(results.estimates['default'].models['final iteration estimate'], results.dataset,
dof_calc_method="all")
self.assertTrue(nSigma < 5.0) # so far we just know that this should roughly work -- how to make TD-GST robus is still an open research topic
if __name__ == "__main__":
unittest.main(verbosity=2)