27 #include <type_traits> 30 template<
typename MatrixT>
31 using KernelComplexT =
typename std::remove_reference<decltype(std::declval<MatrixT&>()[0])>::type;
33 template<
typename MatrixT>
56 for (
int current_idx_pair=current_idx + index_step_target; current_idx_pair<
matrix_size; current_idx_pair=current_idx_pair+(index_step_target << 1) ) {
58 for(
int idx=0; idx<index_step_target; idx++) {
61 int current_idx_loc = current_idx + idx;
62 int current_idx_pair_loc = current_idx_pair + idx;
64 int row_offset = current_idx_loc*input.stride;
65 int row_offset_pair = current_idx_pair_loc*input.stride;
67 if ( control_qbit<0 || ((current_idx_loc >> control_qbit) & 1) ) {
69 for (
int col_idx=0; col_idx<input.cols; col_idx++) {
71 int index = row_offset+col_idx;
72 int index_pair = row_offset_pair+col_idx;
74 ComplexT element = input[index];
75 ComplexT element_pair = input[index_pair];
77 ComplexT tmp1 =
mult(u3_1qbit[0], element);
78 ComplexT tmp2 =
mult(u3_1qbit[1], element_pair);
80 input[index].real = tmp1.real + tmp2.real;
81 input[index].imag = tmp1.imag + tmp2.imag;
83 tmp1 =
mult(u3_1qbit[2], element);
84 tmp2 =
mult(u3_1qbit[3], element_pair);
86 input[index_pair].real = tmp1.real + tmp2.real;
87 input[index_pair].imag = tmp1.imag + tmp2.imag;
95 memset( input.get_data()+row_offset, 0, input.cols*
sizeof(ComplexT));
96 memset( input.get_data()+row_offset_pair, 0, input.cols*
sizeof(ComplexT));
109 current_idx = current_idx + (index_step_target << 1);
129 template<
typename MatrixT>
139 for (
int row_idx = 0; row_idx < input.rows; row_idx++) {
141 int row_offset = row_idx * input.stride;
143 int current_idx_pair = index_step_target;
145 while (current_idx_pair < input.cols) {
147 for (
int idx = 0; idx < index_step_target; idx++) {
149 int current_idx_loc = current_idx + idx;
150 int current_idx_pair_loc = current_idx_pair + idx;
152 if (control_qbit < 0 || ((current_idx_loc >> control_qbit) & 1)) {
154 int index = row_offset + current_idx_loc;
155 int index_pair = row_offset + current_idx_pair_loc;
157 ComplexT element = input[index];
158 ComplexT element_pair = input[index_pair];
160 ComplexT tmp1 =
mult(u3_1qbit[0], element);
161 ComplexT tmp2 =
mult(u3_1qbit[2], element_pair);
162 input[index].real = tmp1.real + tmp2.real;
163 input[index].imag = tmp1.imag + tmp2.imag;
165 tmp1 =
mult(u3_1qbit[1], element);
166 tmp2 =
mult(u3_1qbit[3], element_pair);
167 input[index_pair].real = tmp1.real + tmp2.real;
168 input[index_pair].imag = tmp1.imag + tmp2.imag;
172 current_idx += (index_step_target << 1);
173 current_idx_pair += (index_step_target << 1);
QGD_Complex16 mult(QGD_Complex16 &a, QGD_Complex16 &b)
Call to calculate the product of two complex scalars.
Double-precision complex matrix (float64).
Single-precision complex matrix (float32).