pyGSTi 0.9.12__cp39-cp39-win_amd64.whl → 0.9.13__cp39-cp39-win_amd64.whl

Sign up to get free protection for your applications and to get access to all the features.
Files changed (225) hide show
  1. pyGSTi-0.9.13.dist-info/METADATA +197 -0
  2. {pyGSTi-0.9.12.dist-info → pyGSTi-0.9.13.dist-info}/RECORD +211 -220
  3. {pyGSTi-0.9.12.dist-info → pyGSTi-0.9.13.dist-info}/WHEEL +1 -1
  4. pygsti/_version.py +2 -2
  5. pygsti/algorithms/contract.py +1 -1
  6. pygsti/algorithms/core.py +62 -35
  7. pygsti/algorithms/fiducialpairreduction.py +95 -110
  8. pygsti/algorithms/fiducialselection.py +17 -8
  9. pygsti/algorithms/gaugeopt.py +2 -2
  10. pygsti/algorithms/germselection.py +87 -77
  11. pygsti/algorithms/mirroring.py +0 -388
  12. pygsti/algorithms/randomcircuit.py +165 -1333
  13. pygsti/algorithms/rbfit.py +0 -234
  14. pygsti/baseobjs/basis.py +94 -396
  15. pygsti/baseobjs/errorgenbasis.py +0 -132
  16. pygsti/baseobjs/errorgenspace.py +0 -10
  17. pygsti/baseobjs/label.py +52 -168
  18. pygsti/baseobjs/opcalc/fastopcalc.cp39-win_amd64.pyd +0 -0
  19. pygsti/baseobjs/opcalc/fastopcalc.pyx +2 -2
  20. pygsti/baseobjs/polynomial.py +13 -595
  21. pygsti/baseobjs/protectedarray.py +72 -132
  22. pygsti/baseobjs/statespace.py +1 -0
  23. pygsti/circuits/__init__.py +1 -1
  24. pygsti/circuits/circuit.py +753 -504
  25. pygsti/circuits/circuitconstruction.py +0 -4
  26. pygsti/circuits/circuitlist.py +47 -5
  27. pygsti/circuits/circuitparser/__init__.py +8 -8
  28. pygsti/circuits/circuitparser/fastcircuitparser.cp39-win_amd64.pyd +0 -0
  29. pygsti/circuits/circuitstructure.py +3 -3
  30. pygsti/circuits/cloudcircuitconstruction.py +27 -14
  31. pygsti/data/datacomparator.py +4 -9
  32. pygsti/data/dataset.py +51 -46
  33. pygsti/data/hypothesistest.py +0 -7
  34. pygsti/drivers/bootstrap.py +0 -49
  35. pygsti/drivers/longsequence.py +46 -10
  36. pygsti/evotypes/basereps_cython.cp39-win_amd64.pyd +0 -0
  37. pygsti/evotypes/chp/opreps.py +0 -61
  38. pygsti/evotypes/chp/statereps.py +0 -32
  39. pygsti/evotypes/densitymx/effectcreps.cpp +9 -10
  40. pygsti/evotypes/densitymx/effectreps.cp39-win_amd64.pyd +0 -0
  41. pygsti/evotypes/densitymx/effectreps.pyx +1 -1
  42. pygsti/evotypes/densitymx/opreps.cp39-win_amd64.pyd +0 -0
  43. pygsti/evotypes/densitymx/opreps.pyx +2 -2
  44. pygsti/evotypes/densitymx/statereps.cp39-win_amd64.pyd +0 -0
  45. pygsti/evotypes/densitymx/statereps.pyx +1 -1
  46. pygsti/evotypes/densitymx_slow/effectreps.py +7 -23
  47. pygsti/evotypes/densitymx_slow/opreps.py +16 -23
  48. pygsti/evotypes/densitymx_slow/statereps.py +10 -3
  49. pygsti/evotypes/evotype.py +39 -2
  50. pygsti/evotypes/stabilizer/effectreps.cp39-win_amd64.pyd +0 -0
  51. pygsti/evotypes/stabilizer/effectreps.pyx +0 -4
  52. pygsti/evotypes/stabilizer/opreps.cp39-win_amd64.pyd +0 -0
  53. pygsti/evotypes/stabilizer/opreps.pyx +0 -4
  54. pygsti/evotypes/stabilizer/statereps.cp39-win_amd64.pyd +0 -0
  55. pygsti/evotypes/stabilizer/statereps.pyx +1 -5
  56. pygsti/evotypes/stabilizer/termreps.cp39-win_amd64.pyd +0 -0
  57. pygsti/evotypes/stabilizer/termreps.pyx +0 -7
  58. pygsti/evotypes/stabilizer_slow/effectreps.py +0 -22
  59. pygsti/evotypes/stabilizer_slow/opreps.py +0 -4
  60. pygsti/evotypes/stabilizer_slow/statereps.py +0 -4
  61. pygsti/evotypes/statevec/effectreps.cp39-win_amd64.pyd +0 -0
  62. pygsti/evotypes/statevec/effectreps.pyx +1 -1
  63. pygsti/evotypes/statevec/opreps.cp39-win_amd64.pyd +0 -0
  64. pygsti/evotypes/statevec/opreps.pyx +2 -2
  65. pygsti/evotypes/statevec/statereps.cp39-win_amd64.pyd +0 -0
  66. pygsti/evotypes/statevec/statereps.pyx +1 -1
  67. pygsti/evotypes/statevec/termreps.cp39-win_amd64.pyd +0 -0
  68. pygsti/evotypes/statevec/termreps.pyx +0 -7
  69. pygsti/evotypes/statevec_slow/effectreps.py +0 -3
  70. pygsti/evotypes/statevec_slow/opreps.py +0 -5
  71. pygsti/extras/__init__.py +0 -1
  72. pygsti/extras/drift/signal.py +1 -1
  73. pygsti/extras/drift/stabilityanalyzer.py +3 -1
  74. pygsti/extras/interpygate/__init__.py +12 -0
  75. pygsti/extras/interpygate/core.py +0 -36
  76. pygsti/extras/interpygate/process_tomography.py +44 -10
  77. pygsti/extras/rpe/rpeconstruction.py +0 -2
  78. pygsti/forwardsims/__init__.py +1 -0
  79. pygsti/forwardsims/forwardsim.py +50 -93
  80. pygsti/forwardsims/mapforwardsim.py +78 -20
  81. pygsti/forwardsims/mapforwardsim_calc_densitymx.cp39-win_amd64.pyd +0 -0
  82. pygsti/forwardsims/mapforwardsim_calc_densitymx.pyx +65 -66
  83. pygsti/forwardsims/mapforwardsim_calc_generic.py +91 -13
  84. pygsti/forwardsims/matrixforwardsim.py +72 -17
  85. pygsti/forwardsims/termforwardsim.py +9 -111
  86. pygsti/forwardsims/termforwardsim_calc_stabilizer.cp39-win_amd64.pyd +0 -0
  87. pygsti/forwardsims/termforwardsim_calc_statevec.cp39-win_amd64.pyd +0 -0
  88. pygsti/forwardsims/termforwardsim_calc_statevec.pyx +0 -651
  89. pygsti/forwardsims/torchfwdsim.py +265 -0
  90. pygsti/forwardsims/weakforwardsim.py +2 -2
  91. pygsti/io/__init__.py +1 -2
  92. pygsti/io/mongodb.py +0 -2
  93. pygsti/io/stdinput.py +6 -22
  94. pygsti/layouts/copalayout.py +10 -12
  95. pygsti/layouts/distlayout.py +0 -40
  96. pygsti/layouts/maplayout.py +103 -25
  97. pygsti/layouts/matrixlayout.py +99 -60
  98. pygsti/layouts/prefixtable.py +1534 -52
  99. pygsti/layouts/termlayout.py +1 -1
  100. pygsti/modelmembers/instruments/instrument.py +3 -3
  101. pygsti/modelmembers/instruments/tpinstrument.py +2 -2
  102. pygsti/modelmembers/modelmember.py +0 -17
  103. pygsti/modelmembers/operations/__init__.py +3 -4
  104. pygsti/modelmembers/operations/affineshiftop.py +206 -0
  105. pygsti/modelmembers/operations/composederrorgen.py +1 -1
  106. pygsti/modelmembers/operations/composedop.py +1 -24
  107. pygsti/modelmembers/operations/denseop.py +5 -5
  108. pygsti/modelmembers/operations/eigpdenseop.py +2 -2
  109. pygsti/modelmembers/operations/embeddederrorgen.py +1 -1
  110. pygsti/modelmembers/operations/embeddedop.py +0 -1
  111. pygsti/modelmembers/operations/experrorgenop.py +5 -2
  112. pygsti/modelmembers/operations/fullarbitraryop.py +1 -0
  113. pygsti/modelmembers/operations/fullcptpop.py +2 -2
  114. pygsti/modelmembers/operations/fulltpop.py +28 -6
  115. pygsti/modelmembers/operations/fullunitaryop.py +5 -4
  116. pygsti/modelmembers/operations/lindbladcoefficients.py +93 -78
  117. pygsti/modelmembers/operations/lindbladerrorgen.py +268 -441
  118. pygsti/modelmembers/operations/linearop.py +7 -27
  119. pygsti/modelmembers/operations/opfactory.py +1 -1
  120. pygsti/modelmembers/operations/repeatedop.py +1 -24
  121. pygsti/modelmembers/operations/staticstdop.py +1 -1
  122. pygsti/modelmembers/povms/__init__.py +3 -3
  123. pygsti/modelmembers/povms/basepovm.py +7 -36
  124. pygsti/modelmembers/povms/complementeffect.py +4 -9
  125. pygsti/modelmembers/povms/composedeffect.py +0 -320
  126. pygsti/modelmembers/povms/computationaleffect.py +1 -1
  127. pygsti/modelmembers/povms/computationalpovm.py +3 -1
  128. pygsti/modelmembers/povms/effect.py +3 -5
  129. pygsti/modelmembers/povms/marginalizedpovm.py +3 -81
  130. pygsti/modelmembers/povms/tppovm.py +74 -2
  131. pygsti/modelmembers/states/__init__.py +2 -5
  132. pygsti/modelmembers/states/composedstate.py +0 -317
  133. pygsti/modelmembers/states/computationalstate.py +3 -3
  134. pygsti/modelmembers/states/cptpstate.py +4 -4
  135. pygsti/modelmembers/states/densestate.py +10 -8
  136. pygsti/modelmembers/states/fullpurestate.py +0 -24
  137. pygsti/modelmembers/states/purestate.py +1 -1
  138. pygsti/modelmembers/states/state.py +5 -6
  139. pygsti/modelmembers/states/tpstate.py +28 -10
  140. pygsti/modelmembers/term.py +3 -6
  141. pygsti/modelmembers/torchable.py +50 -0
  142. pygsti/modelpacks/_modelpack.py +1 -1
  143. pygsti/modelpacks/smq1Q_ZN.py +3 -1
  144. pygsti/modelpacks/smq2Q_XXYYII.py +2 -1
  145. pygsti/modelpacks/smq2Q_XY.py +3 -3
  146. pygsti/modelpacks/smq2Q_XYI.py +2 -2
  147. pygsti/modelpacks/smq2Q_XYICNOT.py +3 -3
  148. pygsti/modelpacks/smq2Q_XYICPHASE.py +3 -3
  149. pygsti/modelpacks/smq2Q_XYXX.py +1 -1
  150. pygsti/modelpacks/smq2Q_XYZICNOT.py +3 -3
  151. pygsti/modelpacks/smq2Q_XYZZ.py +1 -1
  152. pygsti/modelpacks/stdtarget.py +0 -121
  153. pygsti/models/cloudnoisemodel.py +1 -2
  154. pygsti/models/explicitcalc.py +3 -3
  155. pygsti/models/explicitmodel.py +3 -13
  156. pygsti/models/fogistore.py +5 -3
  157. pygsti/models/localnoisemodel.py +1 -2
  158. pygsti/models/memberdict.py +0 -12
  159. pygsti/models/model.py +801 -68
  160. pygsti/models/modelconstruction.py +4 -4
  161. pygsti/models/modelnoise.py +2 -2
  162. pygsti/models/modelparaminterposer.py +1 -1
  163. pygsti/models/oplessmodel.py +1 -1
  164. pygsti/models/qutrit.py +15 -14
  165. pygsti/objectivefns/objectivefns.py +75 -140
  166. pygsti/objectivefns/wildcardbudget.py +2 -7
  167. pygsti/optimize/__init__.py +1 -0
  168. pygsti/optimize/arraysinterface.py +28 -0
  169. pygsti/optimize/customcg.py +0 -12
  170. pygsti/optimize/customlm.py +129 -323
  171. pygsti/optimize/customsolve.py +2 -2
  172. pygsti/optimize/optimize.py +0 -84
  173. pygsti/optimize/simplerlm.py +841 -0
  174. pygsti/optimize/wildcardopt.py +19 -598
  175. pygsti/protocols/confidenceregionfactory.py +28 -14
  176. pygsti/protocols/estimate.py +31 -14
  177. pygsti/protocols/gst.py +238 -142
  178. pygsti/protocols/modeltest.py +19 -12
  179. pygsti/protocols/protocol.py +9 -37
  180. pygsti/protocols/rb.py +450 -79
  181. pygsti/protocols/treenode.py +8 -2
  182. pygsti/protocols/vb.py +108 -206
  183. pygsti/protocols/vbdataframe.py +1 -1
  184. pygsti/report/factory.py +0 -15
  185. pygsti/report/fogidiagram.py +1 -17
  186. pygsti/report/modelfunction.py +12 -3
  187. pygsti/report/mpl_colormaps.py +1 -1
  188. pygsti/report/plothelpers.py +11 -3
  189. pygsti/report/report.py +16 -0
  190. pygsti/report/reportables.py +41 -37
  191. pygsti/report/templates/offline/pygsti_dashboard.css +6 -0
  192. pygsti/report/templates/offline/pygsti_dashboard.js +12 -0
  193. pygsti/report/workspace.py +2 -14
  194. pygsti/report/workspaceplots.py +328 -505
  195. pygsti/tools/basistools.py +9 -36
  196. pygsti/tools/edesigntools.py +124 -96
  197. pygsti/tools/fastcalc.cp39-win_amd64.pyd +0 -0
  198. pygsti/tools/fastcalc.pyx +35 -81
  199. pygsti/tools/internalgates.py +151 -15
  200. pygsti/tools/jamiolkowski.py +5 -5
  201. pygsti/tools/lindbladtools.py +19 -11
  202. pygsti/tools/listtools.py +0 -114
  203. pygsti/tools/matrixmod2.py +1 -1
  204. pygsti/tools/matrixtools.py +173 -339
  205. pygsti/tools/nameddict.py +1 -1
  206. pygsti/tools/optools.py +154 -88
  207. pygsti/tools/pdftools.py +0 -25
  208. pygsti/tools/rbtheory.py +3 -320
  209. pygsti/tools/slicetools.py +64 -12
  210. pyGSTi-0.9.12.dist-info/METADATA +0 -157
  211. pygsti/algorithms/directx.py +0 -711
  212. pygsti/evotypes/qibo/__init__.py +0 -33
  213. pygsti/evotypes/qibo/effectreps.py +0 -78
  214. pygsti/evotypes/qibo/opreps.py +0 -376
  215. pygsti/evotypes/qibo/povmreps.py +0 -98
  216. pygsti/evotypes/qibo/statereps.py +0 -174
  217. pygsti/extras/rb/__init__.py +0 -13
  218. pygsti/extras/rb/benchmarker.py +0 -957
  219. pygsti/extras/rb/dataset.py +0 -378
  220. pygsti/extras/rb/io.py +0 -814
  221. pygsti/extras/rb/simulate.py +0 -1020
  222. pygsti/io/legacyio.py +0 -385
  223. pygsti/modelmembers/povms/denseeffect.py +0 -142
  224. {pyGSTi-0.9.12.dist-info → pyGSTi-0.9.13.dist-info}/LICENSE +0 -0
  225. {pyGSTi-0.9.12.dist-info → pyGSTi-0.9.13.dist-info}/top_level.txt +0 -0
@@ -8,78 +8,73 @@ import warnings as _warnings
8
8
  from pygsti.tools import lindbladtools as _lt
9
9
  from pygsti.tools import matrixtools as _mt
10
10
  from pygsti.tools import optools as _ot
11
+ from pygsti.tools import fastcalc as _fc
11
12
  from pygsti.baseobjs.basis import Basis as _Basis, BuiltinBasis as _BuiltinBasis
12
13
  from pygsti.modelmembers import term as _term
13
14
  from pygsti.baseobjs.polynomial import Polynomial as _Polynomial
14
15
  from pygsti.baseobjs.nicelyserializable import NicelySerializable as _NicelySerializable
15
16
 
17
+ from functools import lru_cache
18
+
16
19
  IMAG_TOL = 1e-7 # tolerance for imaginary part being considered zero
17
20
 
18
21
 
19
22
  class LindbladCoefficientBlock(_NicelySerializable):
20
- """ SCRATCH:
21
- This routine computes the Hamiltonian and Non-Hamiltonian ("other")
22
- superoperator generators which correspond to the terms of the Lindblad
23
- expression:
24
-
25
- L(rho) = sum_i( h_i [A_i,rho] ) +
26
- sum_ij( o_ij * (B_i rho B_j^dag -
27
- 0.5( rho B_j^dag B_i + B_j^dag B_i rho) ) )
28
-
29
- where {A_i} and {B_i} are bases (possibly the same) for Hilbert Schmidt
30
- (density matrix) space with the identity element removed so that each
31
- A_i and B_i are traceless. If we write L(rho) in terms of superoperators
32
- H_i and O_ij,
33
-
34
- L(rho) = sum_i( h_i H_i(rho) ) + sum_ij( o_ij O_ij(rho) )
35
-
36
- then this function computes the matrices for H_i and O_ij using the given
37
- density matrix basis. Thus, if `dmbasis` is expressed in the standard
38
- basis (as it should be), the returned matrices are also in this basis.
39
-
40
- If these elements are used as projectors it may be usedful to normalize
41
- them (by setting `normalize=True`). Note, however, that these projectors
42
- are not all orthogonal - in particular the O_ij's are not orthogonal to
43
- one another.
44
-
45
- Parameters
46
- ----------
47
- dmbasis_ham : list
48
- A list of basis matrices {B_i} *including* the identity as the first
49
- element, for the returned Hamiltonian-type error generators. This
50
- argument is easily obtained by call to :func:`pp_matrices` or a
51
- similar function. The matrices are expected to be in the standard
52
- basis, and should be traceless except for the identity. Matrices
53
- should be NumPy arrays or SciPy CSR sparse matrices.
54
-
55
- dmbasis_other : list
56
- A list of basis matrices {B_i} *including* the identity as the first
57
- element, for the returned Stochastic-type error generators. This
58
- argument is easily obtained by call to :func:`pp_matrices` or a
59
- similar function. The matrices are expected to be in the standard
60
- basis, and should be traceless except for the identity. Matrices
61
- should be NumPy arrays or SciPy CSR sparse matrices.
62
-
63
- normalize : bool
64
- Whether or not generators should be normalized so that
65
- numpy.linalg.norm(generator.flat) == 1.0 Note that the generators
66
- will still, in general, be non-orthogonal.
67
-
68
- other_mode : {"diagonal", "diag_affine", "all"}
69
- Which non-Hamiltonian Lindblad error generators to construct.
70
- Allowed values are: `"diagonal"` (only the diagonal Stochastic
71
- generators are returned; that is, the generators corresponding to the
72
- `i==j` terms in the Lindblad expression.), `"diag_affine"` (diagonal +
73
- affine generators), and `"all"` (all generators).
23
+ """
24
+ Class for storing and managing the parameters associated with particular subblocks of error-generator
25
+ parameters. Responsible for management of different internal representations utilized when employing
26
+ various error generator constraints.
74
27
  """
75
28
 
76
29
  _superops_cache = {} # a custom cache for create_lindblad_term_superoperators method calls
77
30
 
78
31
  def __init__(self, block_type, basis, basis_element_labels=None, initial_block_data=None, param_mode='static',
79
32
  truncate=False):
33
+ """
34
+ Parameters
35
+ ----------
36
+ block_type : str
37
+ String specifying the type of error generator parameters contained within this block. Allowed
38
+ values are 'ham' (for Hamiltonian error generators), 'other_diagonal' (for Pauli stochastic error generators),
39
+ and 'other' (for Pauli stochastic, Pauli correlation and active error generators).
40
+
41
+ basis : `Basis`
42
+ `Basis` object to be used by this coefficient block. Not this must be an actual `Basis` object, and not
43
+ a string (as the coefficient block doesn't have the requisite dimensionality information needed for casting).
44
+
45
+ basis_element_labels : list or tuple of str
46
+ Iterable of strings corresponding to the basis element subscripts used by the error generators managed by
47
+ this coefficient block.
48
+
49
+ initial_block_data : _np.ndarray, optional (default None)
50
+ Numpy array with initial parameter values to use in setting initial state of this coefficient block.
51
+
52
+ param_mode : str, optional (default 'static')
53
+ String specifying the type of internal parameterization used by this coefficient block. Allowed options are:
54
+
55
+ - For all block types: 'static'
56
+ - For 'ham': 'elements'
57
+ - For 'other_diagonal': 'elements', 'cholesky', 'depol', 'reldepol'
58
+ - For 'other': 'elements', 'cholesky'
59
+
60
+ Note that the most commonly encounted settings in practice are 'elements' and 'cholesky',
61
+ which when used in the right combination are utilized in the construction of GLND and CPTPLND
62
+ parameterized models. For both GLND and CPTPLND the 'ham' block used the 'elements' `param_mode`.
63
+ GLND the 'other' block uses 'elements', and for CPTPLND it uses 'cholesky'.
64
+
65
+ 'depol' and 'reldepol' are special modes used only for Pauli stochastic only coefficient blocks
66
+ (i.e. 'other_diagonal'), and correspond to special reduced parameterizations applicable to depolarizing
67
+ channels. (TODO: Add better explanation of the difference between depol and reldepol).
68
+
69
+ truncate : bool, optional (default False)
70
+ Flag specifying whether to truncate the parameters given by `initial_block_data` in order to meet
71
+ constraints (e.g. to preserve CPTP) when necessary. If False, then an error is thrown when the
72
+ given intial data cannot be parameterized as specified.
73
+ """
74
+
80
75
  super().__init__()
81
76
  self._block_type = block_type # 'ham' or 'other' or 'other_diagonal'
82
- self._param_mode = param_mode # 'static', 'elements', 'cholesky', or 'real_cholesky', 'depol', 'reldepol'
77
+ self._param_mode = param_mode # 'static', 'elements', 'cholesky', 'depol', 'reldepol'
83
78
  self._basis = basis # must be a full Basis object, not just a string, as we otherwise don't know dimension
84
79
  self._bel_labels = tuple(basis_element_labels) if (basis_element_labels is not None) \
85
80
  else tuple(basis.labels[1:]) # Note: don't include identity
@@ -195,7 +190,7 @@ class LindbladCoefficientBlock(_NicelySerializable):
195
190
  if sparse:
196
191
  #Note: complex OK here sometimes, as only linear combos of "other" gens
197
192
  # (like (i,j) + (j,i) terms) need to be real.
198
- superops = [_mt.safe_dot(leftTrans, _mt.safe_dot(mx, rightTrans)) for mx in superops]
193
+ superops = [leftTrans @ (mx @ rightTrans) for mx in superops]
199
194
  for mx in superops: mx.sort_indices()
200
195
  else:
201
196
  #superops = _np.einsum("ik,akl,lj->aij", leftTrans, superops, rightTrans)
@@ -816,12 +811,19 @@ class LindbladCoefficientBlock(_NicelySerializable):
816
811
  # encodes a lower-triangular matrix "cache_mx" via:
817
812
  # cache_mx[i,i] = params[i,i]
818
813
  # cache_mx[i,j] = params[i,j] + 1j*params[j,i] (i > j)
814
+
819
815
  cache_mx = self._cache_mx
820
- iparams = 1j * params
821
- for i in range(num_bels):
822
- cache_mx[i, i] = params[i, i]
823
- cache_mx[i, :i] = params[i, :i] + iparams[:i, i]
824
816
 
817
+ params_upper_indices = _fc.fast_triu_indices(num_bels)
818
+ params_upper = 1j*params[params_upper_indices]
819
+ params_lower = (params.T)[params_upper_indices]
820
+
821
+ cache_mx_trans = cache_mx.T
822
+ cache_mx_trans[params_upper_indices] = params_lower + params_upper
823
+
824
+ diag_indices = cached_diag_indices(num_bels)
825
+ cache_mx[diag_indices] = params[diag_indices]
826
+
825
827
  #The matrix of (complex) "other"-coefficients is build by assuming
826
828
  # cache_mx is its Cholesky decomp; means otherCoeffs is pos-def.
827
829
 
@@ -830,27 +832,28 @@ class LindbladCoefficientBlock(_NicelySerializable):
830
832
  # matrix, but we don't care about this uniqueness criteria and so
831
833
  # the diagonal els of cache_mx can be negative and that's fine -
832
834
  # block_data will still be posdef.
833
- self.block_data[:, :] = _np.dot(cache_mx, cache_mx.T.conjugate())
835
+ self.block_data[:, :] = cache_mx@cache_mx.T.conj()
834
836
 
835
- #DEBUG - test for pos-def
836
- #evals = _np.linalg.eigvalsh(block_data)
837
- #DEBUG_TOL = 1e-16; #print("EVALS DEBUG = ",evals)
838
- #assert(all([ev >= -DEBUG_TOL for ev in evals]))
839
837
 
840
838
  elif self._param_mode == "elements": # params mx stores block_data (hermitian) directly
841
839
  #params holds block_data real and imaginary parts directly
842
- iparams = 1j * params
843
- for i in range(num_bels):
844
- self.block_data[i, i] = params[i, i]
845
- self.block_data[i, :i] = params[i, :i] + iparams[:i, i]
846
- self.block_data[:i, i] = params[i, :i] - iparams[:i, i]
840
+ params_upper_indices = _fc.fast_triu_indices(num_bels)
841
+ params_upper = -1j*params[params_upper_indices]
842
+ params_lower = (params.T)[params_upper_indices]
843
+
844
+ block_data_trans = self.block_data.T
845
+ self.block_data[params_upper_indices] = params_lower + params_upper
846
+ block_data_trans[params_upper_indices] = params_lower - params_upper
847
+
848
+ diag_indices = cached_diag_indices(num_bels)
849
+ self.block_data[diag_indices] = params[diag_indices]
850
+
847
851
  else:
848
852
  raise ValueError("Internal error: invalid parameter mode (%s) for block type %s!"
849
853
  % (self._param_mode, self._block_type))
850
854
  else:
851
855
  raise ValueError("Internal error: invalid block type!")
852
856
 
853
- #def paramvals_to_coefficients_deriv(self, parameter_values, cache_mx=None):
854
857
  def deriv_wrt_params(self, v=None):
855
858
  """
856
859
  Construct derivative of Lindblad coefficients (for this block) from a set of parameter values.
@@ -1112,11 +1115,11 @@ class LindbladCoefficientBlock(_NicelySerializable):
1112
1115
  if self._param_mode == "depol":
1113
1116
  #d2Odp2 = _np.einsum('alj->lj', self.otherGens)[:,:,None,None] * 2
1114
1117
  d2Odp2 = _np.sum(superops, axis=0)[:, :, None, None] * 2
1115
- elif self.parameterization.param_mode == "cptp":
1118
+ elif self._param_mode == "cholesky":
1116
1119
  assert(nP == num_bels)
1117
1120
  #d2Odp2 = _np.einsum('alj,aq->ljaq', self.otherGens, 2*_np.identity(nP,'d'))
1118
1121
  d2Odp2 = _np.transpose(superops, (1, 2, 0))[:, :, :, None] * 2 * _np.identity(nP, 'd')
1119
- else: # param_mode == "unconstrained" or "reldepol"
1122
+ else: # param_mode == "elements" or "reldepol"
1120
1123
  assert(nP == num_bels)
1121
1124
  d2Odp2 = _np.zeros((superops.shape[1], superops.shape[2], nP, nP), 'd')
1122
1125
 
@@ -1124,7 +1127,10 @@ class LindbladCoefficientBlock(_NicelySerializable):
1124
1127
  if self._param_mode == "cholesky":
1125
1128
  if superops_are_flat: # then un-flatten
1126
1129
  superops = superops.reshape((num_bels, num_bels, superops.shape[1], superops.shape[2]))
1127
- d2Odp2 = _np.zeros([superops.shape[2], superops.shape[3], nP, nP, nP, nP], 'complex')
1130
+ sqrt_nP = _np.sqrt(nP)
1131
+ snP = int(sqrt_nP)
1132
+ assert snP == sqrt_nP == num_bels
1133
+ d2Odp2 = _np.zeros([superops.shape[2], superops.shape[3], snP, snP, snP, snP], 'complex')
1128
1134
  # yikes! maybe make this SPARSE in future?
1129
1135
 
1130
1136
  #Note: correspondence w/Erik's notes: a=alpha, b=beta, q=gamma, r=delta
@@ -1136,11 +1142,11 @@ class LindbladCoefficientBlock(_NicelySerializable):
1136
1142
  parameter indices s.t. ab > base and qr > base. If
1137
1143
  ab_inc_eq == True then the > becomes a >=, and likewise
1138
1144
  for qr_inc_eq. Used for looping over nonzero hessian els. """
1139
- for _base in range(nP):
1145
+ for _base in range(snP):
1140
1146
  start_ab = _base if ab_inc_eq else _base + 1
1141
1147
  start_qr = _base if qr_inc_eq else _base + 1
1142
- for _ab in range(start_ab, nP):
1143
- for _qr in range(start_qr, nP):
1148
+ for _ab in range(start_ab, snP):
1149
+ for _qr in range(start_qr, snP):
1144
1150
  yield (_base, _ab, _qr)
1145
1151
 
1146
1152
  for base, a, q in iter_base_ab_qr(True, True): # Case1: base=b=r, ab=a, qr=q
@@ -1153,7 +1159,12 @@ class LindbladCoefficientBlock(_NicelySerializable):
1153
1159
  d2Odp2[:, :, base, b, base, r] = superops[b, r] + superops[r, b]
1154
1160
 
1155
1161
  elif self._param_mode == 'elements': # unconstrained
1156
- d2Odp2 = _np.zeros([superops.shape[2], superops.shape[3], nP, nP, nP, nP], 'd') # all params linear
1162
+ if superops_are_flat: # then un-flatten
1163
+ superops = superops.reshape((num_bels, num_bels, superops.shape[1], superops.shape[2]))
1164
+ sqrt_nP = _np.sqrt(nP)
1165
+ snP = int(sqrt_nP)
1166
+ assert snP == sqrt_nP == num_bels
1167
+ d2Odp2 = _np.zeros([superops.shape[2], superops.shape[3], snP, snP, snP, snP], 'd') # all params linear
1157
1168
  else:
1158
1169
  raise ValueError("Internal error: invalid parameter mode (%s) for block type %s!"
1159
1170
  % (self._param_mode, self._block_type))
@@ -1204,3 +1215,7 @@ class LindbladCoefficientBlock(_NicelySerializable):
1204
1215
  if len(self._bel_labels) < 10:
1205
1216
  s += " Coefficients are:\n" + str(_np.round(self.block_data, 4))
1206
1217
  return s
1218
+
1219
+ @lru_cache(maxsize=16)
1220
+ def cached_diag_indices(n):
1221
+ return _np.diag_indices(n)