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
use crate::{
StabilizerCHForm,
error::{Error, Result},
};
impl StabilizerCHForm {
// Applies the Pauli-X gate to the qubit at index `qarg`.
//
// Time complexity: O(n)
//
// See around eq.(48) of arXiv:1808.00128 for details.
pub(crate) fn left_multiply_x(&mut self, qarg: usize) -> Result<()> {
if qarg >= self.n {
return Err(Error::QubitIndexOutOfBounds(qarg, self.n));
}
let f_row = self.mat_f.row(qarg);
let m_row = self.mat_m.row(qarg);
// calculate beta appearing in eq.(49) of arXiv:1808.00128
let beta = m_row
.iter()
.zip(f_row.iter())
.zip(self.vec_v.iter())
.zip(self.vec_s.iter())
.fold(false, |acc, (((&m, &f), &v), &s)| {
let t1 = m & !v & s;
let t23 = f & v & (m ^ s);
acc ^ t1 ^ t23
});
if beta {
self.phase_factor = self.phase_factor.flipped();
}
// calculate u appearing in eq.(48) of arXiv:1808.00128
self.vec_s
.iter_mut()
.zip(self.vec_v.iter())
.zip(f_row.iter())
.zip(m_row.iter())
.for_each(|(((s, &v), &f), &m)| {
*s ^= (f & !v) ^ (m & v);
});
self.phase_factor *= self.gamma[qarg];
Ok(())
}
}