Testing utilities which perform linear algebra routines upon reference qvector and qmatrix. These are slow, serial, un-optimised, defensively- designed routines.
More...
|
int | getBitAt (qindex num, int ind) |
|
vector< int > | getBits (qindex num, int numBits) |
|
qindex | getBitsAt (qindex num, vector< int > inds) |
|
qmatrix | getConjugate (qmatrix) |
|
qmatrix | getConjugateTranspose (qmatrix) |
|
qmatrix | getControlledMatrix (qmatrix matrix, int numCtrls) |
|
qvector | getDisceteFourierTransform (qvector in, vector< int > targs) |
|
qvector | getDisceteFourierTransform (qvector) |
|
qmatrix | getExponentialOfDiagonalMatrix (qmatrix) |
|
qmatrix | getExponentialOfNormalisedPauliVector (qreal arg, qreal x, qreal y, qreal z) |
|
qmatrix | getExponentialOfPauliMatrix (qreal arg, qmatrix pauli) |
|
qcomp | getInnerProduct (qvector bra, qvector ket) |
|
qmatrix | getKroneckerProduct (qmatrix, int count) |
|
qmatrix | getKroneckerProduct (qmatrix, qmatrix) |
|
qmatrix | getKroneckerProduct (vector< qmatrix >) |
|
int | getLog2 (qindex) |
|
qmatrix | getMixture (vector< qmatrix > densmatrs, vector< qreal > probs) |
|
qmatrix | getMixture (vector< qvector > statevecs, vector< qreal > probs) |
|
qvector | getNormalised (qvector) |
|
int | getNumPermutations (int n, int k) |
|
qmatrix | getOrthonormalisedRows (qmatrix) |
|
qmatrix | getOuterProduct (qvector ket, qvector bra) |
|
qmatrix | getPartialTrace (qmatrix matrix, vector< int > targets) |
|
qindex | getPow2 (int) |
|
qmatrix | getPowerOfDiagonalMatrix (qmatrix diag, qcomp power) |
|
qmatrix | getProjector (int outcome) |
|
qmatrix | getProjector (vector< int > targets, vector< int > outcomes, int numQubits) |
|
qcomp | getSum (qvector) |
|
qreal | getSum (vector< qreal > vec) |
|
qmatrix | getSuperOperator (vector< qmatrix >) |
|
qcomp | getTrace (qmatrix) |
|
qmatrix | getTranspose (qmatrix) |
|
bool | isApproxCPTP (vector< qmatrix >) |
|
bool | isApproxUnitary (qmatrix) |
|
bool | isDiagonal (qmatrix) |
|
qvector | operator* (const qmatrix &, const qvector &) |
|
qindex | setBitAt (qindex num, int ind, int bit) |
|
qindex | setBitsAt (qindex num, vector< int > inds, qindex bits) |
|
Testing utilities which perform linear algebra routines upon reference qvector and qmatrix. These are slow, serial, un-optimised, defensively- designed routines.
◆ getBitAt()
int getBitAt |
( |
qindex | num, |
|
|
int | ind ) |
Definition at line 47 of file linalg.cpp.
47 {
48 DEMAND( num >= 0 );
49
50 return (num >> ind) & 1;
51}
◆ getBits()
vector< int > getBits |
( |
qindex | num, |
|
|
int | numBits ) |
Definition at line 54 of file linalg.cpp.
54 {
55 DEMAND( numBits > 0 );
56
57
58 vector<int> out(numBits);
59
60 for (int i=0; i<numBits; i++)
61 out[i] = getBitAt(num, i);
62
63 return out;
64}
◆ getBitsAt()
qindex getBitsAt |
( |
qindex | num, |
|
|
vector< int > | inds ) |
Definition at line 67 of file linalg.cpp.
67 {
68 DEMAND( num >= 0 );
69
70 qindex out = 0;
71
72 for (size_t i=0; i<inds.size(); i++)
73 out |= getBitAt(num, inds[i]) << i;
74
75 return out;
76}
◆ getConjugate()
qmatrix getConjugate |
( |
qmatrix | m | ) |
|
Definition at line 281 of file linalg.cpp.
281 {
282
283 for (auto& row : m)
284 for (auto& elem : row)
285 elem = std::conj(elem);
286
287 return m;
288}
◆ getConjugateTranspose()
qmatrix getConjugateTranspose |
( |
qmatrix | m | ) |
|
Definition at line 291 of file linalg.cpp.
291 {
292 DEMAND( m.size() > 0 );
293
294
295
296
297
298
299 qmatrix out(m[0].size(), qvector(m.size()));
300
301 for (size_t r=0; r<out.size(); r++)
302 for (size_t c=0; c<out[0].size(); c++)
303 out[r][c] = std::conj(m[c][r]);
304
305 return out;
306}
◆ getControlledMatrix()
qmatrix getControlledMatrix |
( |
qmatrix | matrix, |
|
|
int | numCtrls ) |
Definition at line 451 of file linalg.cpp.
451 {
452
453 size_t dim = getPow2(numCtrls) * matrix.size();
454 size_t off = dim - matrix.size();
455
458
459 return out;
460}
qmatrix getIdentityMatrix(size_t dim)
void setSubMatrix(qmatrix &dest, qmatrix sub, size_t r, size_t c)
◆ getDisceteFourierTransform() [1/2]
qvector getDisceteFourierTransform |
( |
qvector | in, |
|
|
vector< int > | targs ) |
Definition at line 179 of file linalg.cpp.
179 {
180 DEMAND( in.size() > 0 );
181
182 size_t dim = in.size();
183 qvector out = getZeroVector(dim);
184
185 qindex len = getPow2(targs.size());
186 qreal pi = 3.14159265358979323846;
187 qreal a = 1 / std::sqrt(len);
188 qreal b = 2 * pi / len;
189
190 for (size_t i=0; i<dim; i++) {
191 size_t x = getBitsAt(i, targs);
192 for (size_t y=0; y<len; y++) {
193 qindex j = setBitsAt(i, targs, y);
194 out[j] += a * std::exp(b * x * y * 1_i) * in[i];
195 }
196 }
197
198 return out;
199}
◆ getDisceteFourierTransform() [2/2]
qvector getDisceteFourierTransform |
( |
qvector | in | ) |
|
Definition at line 160 of file linalg.cpp.
160 {
161 DEMAND( in.size() > 0 );
162
163 size_t dim = in.size();
164 qvector out = getZeroVector(dim);
165
166
167 qreal pi = 3.14159265358979323846;
168 qreal a = 1 / std::sqrt(dim);
169 qreal b = 2 * pi / dim;
170
171 for (size_t x=0; x<dim; x++)
172 for (size_t y=0; y<dim; y++)
173 out[x] += a * std::exp(b * x * y * 1_i) * in[y];
174
175 return out;
176}
◆ getExponentialOfDiagonalMatrix()
qmatrix getExponentialOfDiagonalMatrix |
( |
qmatrix | m | ) |
|
Definition at line 336 of file linalg.cpp.
336 {
337 DEMAND( isDiagonal(m) );
338
340
341 for (size_t i=0; i<m.size(); i++)
342 out[i][i] = std::exp(m[i][i]);
343
344 return out;
345}
qmatrix getZeroMatrix(size_t dim)
◆ getExponentialOfNormalisedPauliVector()
qmatrix getExponentialOfNormalisedPauliVector |
( |
qreal | arg, |
|
|
qreal | x, |
|
|
qreal | y, |
|
|
qreal | z ) |
Definition at line 357 of file linalg.cpp.
357 {
358
359
360 qreal n = std::sqrt(x*x + y*y + z*z);
361 x /= n;
362 y /= n;
363 z /= n;
364
366 qmatrix out = std::cos(arg/2)*id - 1_i*std::sin(arg/2)*(
367 x * getPauliMatrix(1) +
368 y * getPauliMatrix(2) +
369 z * getPauliMatrix(3));
370
371 return out;
372}
◆ getExponentialOfPauliMatrix()
qmatrix getExponentialOfPauliMatrix |
( |
qreal | arg, |
|
|
qmatrix | pauli ) |
Definition at line 348 of file linalg.cpp.
348 {
349
350
352 qmatrix out = std::cos(arg/2)*id - 1_i*std::sin(arg/2)*m;
353 return out;
354}
◆ getInnerProduct()
qcomp getInnerProduct |
( |
qvector | bra, |
|
|
qvector | ket ) |
Definition at line 208 of file linalg.cpp.
208 {
209 DEMAND( bra.size() == ket.size() );
210
211 qcomp out = 0;
212
213 for (size_t i=0; i<bra.size(); i++)
214 out += std::conj(bra[i]) * ket[i];
215
216 return out;
217}
◆ getKroneckerProduct() [1/3]
qmatrix getKroneckerProduct |
( |
qmatrix | m, |
|
|
int | count ) |
Definition at line 559 of file linalg.cpp.
559 {
560 DEMAND( count >= 1 );
561
563
564 for (int n=0; n<count; n++)
566
567 return out;
568}
qmatrix getKroneckerProduct(qmatrix a, qmatrix b)
◆ getKroneckerProduct() [2/3]
qmatrix getKroneckerProduct |
( |
qmatrix | a, |
|
|
qmatrix | b ) |
Definition at line 523 of file linalg.cpp.
523 {
524
525
526
527
528
529
530 size_t aRows = a.size();
531 size_t bRows = b.size();
532 size_t aCols = a[0].size();
533 size_t bCols = b[0].size();
534
535 qmatrix out(aRows * bRows, qvector(aCols * bCols));
536
537 for (size_t r=0; r<bRows; r++)
538 for (size_t c=0; c<bCols; c++)
539 for (size_t i=0; i<aRows; i++)
540 for (size_t j=0; j<aCols; j++)
541 out[r+bRows*i][c+bCols*j] = a[i][j] * b[r][c];
542
543 return out;
544}
◆ getKroneckerProduct() [3/3]
qmatrix getKroneckerProduct |
( |
vector< qmatrix > | matrices | ) |
|
Definition at line 547 of file linalg.cpp.
547 {
548
550
551
552 for (auto& m : matrices)
554
555 return out;
556}
◆ getLog2()
Definition at line 28 of file linalg.cpp.
28 {
29 DEMAND( a >= 0 );
30 DEMAND( (a & (a - 1)) == 0 );
31
32 int n = 0;
33 while (a >>= 1)
34 n++;
35
36 return n;
37}
◆ getMixture() [1/2]
qmatrix getMixture |
( |
vector< qmatrix > | densmatrs, |
|
|
vector< qreal > | probs ) |
Definition at line 463 of file linalg.cpp.
463 {
464 DEMAND( densmatrs.size() > 0 );
465
467 for (size_t i=0; i<densmatrs.size(); i++)
468 out += probs[i] * densmatrs[i];
469
470 return out;
471}
◆ getMixture() [2/2]
qmatrix getMixture |
( |
vector< qvector > | statevecs, |
|
|
vector< qreal > | probs ) |
Definition at line 474 of file linalg.cpp.
474 {
475
476 vector<qmatrix> densmatrs(statevecs.size());
477 for (size_t i=0; i<statevecs.size(); i++)
478 densmatrs[i] = getOuterProduct(statevecs[i], statevecs[i]);
479
480 return getMixture(densmatrs, probs);
481}
◆ getNormalised()
qvector getNormalised |
( |
qvector | vec | ) |
|
Definition at line 143 of file linalg.cpp.
143 {
144
145
146 vector<qreal> probs(vec.size());
147 for (size_t i=0; i<vec.size(); i++)
148 probs[i] = std::norm(vec[i]);
149
150
151 qreal norm = getSum(probs);
152 qreal fac = 1 / std::sqrt(norm);
153 for (auto& x : vec)
154 x *= fac;
155
156 return vec;
157}
◆ getNumPermutations()
int getNumPermutations |
( |
int | n, |
|
|
int | k ) |
Definition at line 96 of file linalg.cpp.
96 {
97 DEMAND( n >= k );
98 DEMAND( n <= 11 );
99
100
101 qindex p = 1;
102 for (int t=n-k+1; t<=n; t++)
103 p *= t;
104
105 return p;
106}
◆ getOrthonormalisedRows()
qmatrix getOrthonormalisedRows |
( |
qmatrix | matr | ) |
|
Definition at line 375 of file linalg.cpp.
375 {
376
377
378 for (size_t i=0; i<matr.size(); i++) {
379 qvector row = matr[i];
380
381
382 for (int k=i-1; k>=0; k--) {
383
384
385 qcomp prod = getInnerProduct(matr[k], row);
386
387
388 matr[i] -= prod * matr[k];
389 }
390
391
392 matr[i] = getNormalised(matr[i]);
393 }
394
395
396 return matr;
397}
◆ getOuterProduct()
qmatrix getOuterProduct |
( |
qvector | ket, |
|
|
qvector | bra ) |
Definition at line 220 of file linalg.cpp.
220 {
221 DEMAND( bra.size() == ket.size() );
222
224
225 for (size_t i=0; i<ket.size(); i++)
226 for (size_t j=0; j<ket.size(); j++)
227 out[i][j] = ket[i] * std::conj(bra[j]);
228
229 return out;
230}
◆ getPartialTrace()
qmatrix getPartialTrace |
( |
qmatrix | matrix, |
|
|
vector< int > | targets ) |
Definition at line 422 of file linalg.cpp.
422 {
423 DEMAND( in.size() > getPow2(targets.size()) );
424
425 auto numTargs = targets.size();
426 auto numQubits = getLog2(in.size());
427 auto numTargVals = getPow2(numTargs);
428
430
431 for (qindex v=0; v<numTargVals; v++) {
432
433
435 for (size_t t=0; t<numTargs; t++) {
436 int bit = getBitAt(v, t);
437 matrices[targets[t]] = {
438 {bit? 0.:1.},
439 {bit? 1.:0.}};
440 }
441
444 out += bra * in * ket;
445 }
446
447 return out;
448}
qmatrix getConjugateTranspose(qmatrix m)
◆ getPow2()
Definition at line 40 of file linalg.cpp.
40 {
41 DEMAND( a >= 0 );
42
43 return ((qindex) 1) << a;
44}
◆ getPowerOfDiagonalMatrix()
qmatrix getPowerOfDiagonalMatrix |
( |
qmatrix | diag, |
|
|
qcomp | power ) |
Definition at line 309 of file linalg.cpp.
309 {
310 DEMAND( isDiagonal(m) );
311
313
314
315
316
317
318
319
320 for (size_t i=0; i<m.size(); i++) {
321 bool mIsRe = std::imag(m[i][i]) == 0;
322 bool mIsNeg = std::real(m[i][i]) < 0;
323 bool pIsRe = std::imag(p) == 0;
324 bool pIsInt = std::trunc(std::real(p)) == std::real(p);
325
326
327 out[i][i] = (mIsRe && mIsNeg && pIsRe && pIsInt)?
328 qcomp(std::pow(std::real(m[i][i]), std::real(p)),0):
329 std::pow(m[i][i], p);
330 }
331
332 return out;
333}
◆ getProjector() [1/2]
qmatrix getProjector |
( |
int | outcome | ) |
|
Definition at line 400 of file linalg.cpp.
400 {
401 DEMAND( outcome == 0 || outcome == 1 );
402
404 out[outcome][outcome] = 1.;
405 return out;
406}
◆ getProjector() [2/2]
qmatrix getProjector |
( |
vector< int > | targets, |
|
|
vector< int > | outcomes, |
|
|
int | numQubits ) |
Definition at line 409 of file linalg.cpp.
409 {
410 DEMAND( targets.size() == outcomes.size() );
411 DEMAND( numQubits > *std::max_element(targets.begin(), targets.end()) );
412
413
415 for (size_t i=0; i<targets.size(); i++)
416 matrices[targets[i]] = getProjector(outcomes[i]);
417
419}
◆ getSum() [1/2]
qcomp getSum |
( |
qvector | vec | ) |
|
Definition at line 115 of file linalg.cpp.
115 {
116
117 qcomp sum = qcomp(0,0);
118 qcomp y, t, c=sum;
119
120
121 for (auto& x : vec) {
122 y = x - c;
123 t = sum + y;
124 c = ( t - sum ) - y;
125 sum = t;
126 }
127
128 return sum;
129}
◆ getSum() [2/2]
qreal getSum |
( |
vector< qreal > | vec | ) |
|
Definition at line 132 of file linalg.cpp.
132 {
133
134
135 qvector in = getZeroVector(vec.size());
136 for (size_t i=0; i<in.size(); i++)
137 in[i] = qcomp(vec[i],0);
138
139 return std::real(getSum(in));
140}
◆ getSuperOperator()
qmatrix getSuperOperator |
( |
vector< qmatrix > | matrices | ) |
|
Definition at line 484 of file linalg.cpp.
484 {
485 DEMAND( matrices.size() > 0 );
486
487 size_t dim = matrices[0].size();
488
489
491 for (auto& matr : matrices)
493
494 return out;
495}
◆ getTrace()
qcomp getTrace |
( |
qmatrix | m | ) |
|
Definition at line 259 of file linalg.cpp.
259 {
260
261 qcomp out = 0;
262 for (size_t r=0; r<m.size(); r++)
263 out += m[r][r];
264
265 return out;
266}
◆ getTranspose()
qmatrix getTranspose |
( |
qmatrix | m | ) |
|
Definition at line 269 of file linalg.cpp.
269 {
270
272
273 for (size_t r=0; r<m.size(); r++)
274 for (size_t c=0; c<m.size(); c++)
275 out[r][c] = m[c][r];
276
277 return out;
278}
◆ isApproxCPTP()
bool isApproxCPTP |
( |
vector< qmatrix > | matrices | ) |
|
Definition at line 577 of file linalg.cpp.
577 {
578 DEMAND( matrices.size() >= 1 );
579
580 size_t dim = matrices[0].size();
583
584 for (auto& m : matrices)
586
587 return doMatricesAgree(sum, id);
588}
◆ isApproxUnitary()
bool isApproxUnitary |
( |
qmatrix | m | ) |
|
Definition at line 250 of file linalg.cpp.
250 {
251
252
255 return doMatricesAgree(md, id);
256}
◆ isDiagonal()
bool isDiagonal |
( |
qmatrix | m | ) |
|
Definition at line 239 of file linalg.cpp.
239 {
240
241 for (size_t r=0; r<m.size(); r++)
242 for (size_t c=0; c<m.size(); c++)
243 if (r!=c && m[r][c] != 0_i)
244 return false;
245
246 return true;
247}
◆ operator*()
qvector operator* |
( |
const qmatrix & | m, |
|
|
const qvector & | v ) |
Definition at line 504 of file linalg.cpp.
504 {
505 DEMAND( m.size() == v.size() );
506
507 qvector out = getZeroVector(v.size());
508
509 for (size_t r=0; r<v.size(); r++)
510 for (size_t c=0; c<v.size(); c++)
511 out[r] += m[r][c] * v[c];
512
513 return out;
514}
◆ setBitAt()
qindex setBitAt |
( |
qindex | num, |
|
|
int | ind, |
|
|
int | bit ) |
Definition at line 79 of file linalg.cpp.
79 {
80 DEMAND( num >= 0 );
81
82 qindex one = 1;
83 return (num & ~(one << ind)) | (bit << ind);
84}
◆ setBitsAt()
qindex setBitsAt |
( |
qindex | num, |
|
|
vector< int > | inds, |
|
|
qindex | bits ) |
Definition at line 87 of file linalg.cpp.
87 {
88
89 for (size_t i=0; i<inds.size(); i++)
90 num = setBitAt(num, inds[i], getBitAt(bits, i));
91
92 return num;
93}