Sequential Quantum Gate Decomposer  v1.9.3
Powerful decomposition of general unitarias into one- and two-qubit gates gates
N_Qubit_Decomposition_custom.cpp
Go to the documentation of this file.
1 /*
2 Created on Fri Jun 26 14:13:26 2020
3 Copyright 2020 Peter Rakyta, Ph.D.
4 
5 Licensed under the Apache License, Version 2.0 (the "License");
6 you may not use this file except in compliance with the License.
7 You may obtain a copy of the License at
8 
9  http://www.apache.org/licenses/LICENSE-2.0
10 
11 Unless required by applicable law or agreed to in writing, software
12 distributed under the License is distributed on an "AS IS" BASIS,
13 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 See the License for the specific language governing permissions and
15 limitations under the License.
16 
17 @author: Peter Rakyta, Ph.D.
18 */
26 
27 
28 
34 
35  // BFGS is better for smaller problems, while ADAM for larger ones
36  if ( qbit_num <= 5 ) {
38 
39  // Maximal number of iteartions in the optimization process
41  }
42  else {
44 
45  // Maximal number of iteartions in the optimization process
47  }
48 
49 }
50 
59 N_Qubit_Decomposition_custom::N_Qubit_Decomposition_custom( Matrix Umtx_in, int qbit_num_in, bool optimize_layer_num_in, std::map<std::string, Config_Element>& config, guess_type initial_guess_in= CLOSE_TO_ZERO, int accelerator_num ) : Optimization_Interface(Umtx_in, qbit_num_in, optimize_layer_num_in, config, initial_guess_in, accelerator_num) {
60 
61 
62  // BFGS is better for smaller problems, while ADAM for larger ones
63  if ( qbit_num <= 5 ) {
65 
66  // Maximal number of iteartions in the optimization process
68  }
69  else {
71 
72  // Maximal number of iteartions in the optimization process
74  }
75 
76 }
77 
78 
79 
84 
85 }
86 
87 
88 
93 void
95 
96 
97  //The stringstream input to store the output messages.
98  std::stringstream sstream;
99  sstream << "***************************************************************" << std::endl;
100  sstream << "Starting to disentangle " << qbit_num << "-qubit matrix via custom gate structure" << std::endl;
101  sstream << "***************************************************************" << std::endl << std::endl << std::endl;
102  print(sstream, 1);
103 
104 
105 
106  // temporarily turn off OpenMP parallelism
107 #if BLAS==0 // undefined BLAS
110 #elif BLAS==1 // MKL
111  num_threads = mkl_get_max_threads();
112  MKL_Set_Num_Threads(1);
113 #elif BLAS==2 //OpenBLAS
114  num_threads = openblas_get_num_threads();
115  openblas_set_num_threads(1);
116 #endif
117 
118  //measure the time for the decompositin
119  tbb::tick_count start_time = tbb::tick_count::now();
120 
121 
122 
123 
124  if (optimized_parameters_mtx.size() > 0 ) {
125  sstream.str("");
126  sstream << "cost function of the imported circuit: " << optimization_problem( optimized_parameters_mtx ) << std::endl;
127  print(sstream, 1);
128  }
129 
130 
131  // final tuning of the decomposition parameters
133 
134  // calculating the final error of the decomposition
135  Matrix matrix_decomposed = Umtx.copy();
136  apply_to(optimized_parameters_mtx, matrix_decomposed );
137  calc_decomposition_error( matrix_decomposed );
138 
139 
140  sstream.str("");
141  sstream << "In the decomposition with error = " << decomposition_error << " were used " << layer_num << " layers with:" << std::endl;
142 
143 
144  // get the number of gates used in the decomposition
145  std::map<std::string, int>&& gate_nums = get_gate_nums();
146 
147  for( auto it=gate_nums.begin(); it != gate_nums.end(); it++ ) {
148  sstream << it->second << " " << it->first << " gates" << std::endl;
149  }
150 
151 
152  sstream << std::endl;
153  tbb::tick_count current_time = tbb::tick_count::now();
154 
155  sstream << "--- In total " << (current_time - start_time).seconds() << " seconds elapsed during the decomposition ---" << std::endl;
156  print(sstream, 1);
157 
158 
159 
160 #if BLAS==0 // undefined BLAS
162 #elif BLAS==1 //MKL
163  MKL_Set_Num_Threads(num_threads);
164 #elif BLAS==2 //OpenBLAS
165  openblas_set_num_threads(num_threads);
166 #endif
167 
168 }
169 
170 
171 
172 
173 
174 
175 
176 
177 
178 
void print(const std::stringstream &sstream, int verbose_level=1) const
Call to print output messages in the function of the verbosity level.
Definition: logging.cpp:55
virtual ~N_Qubit_Decomposition_custom()
Destructor of the class.
void set_optimizer(optimization_aglorithms alg_in)
Call to set the optimizer engine to be used in solving the optimization problem.
std::map< std::string, int > get_gate_nums()
Call to get the number of the individual gate types in the list of gates.
N_Qubit_Decomposition_custom()
Nullary constructor of the class.
double optimization_problem(double *parameters)
Evaluate the optimization problem of the optimization.
int layer_num
number of gate layers
Definition: Gates_block.h:48
virtual void apply_to(Matrix_real &parameters_mtx, Matrix &input, int parallel=0)
Call to apply the gate on the input array/matrix Gates_block*input.
int max_outer_iterations
Maximal number of iterations allowed in the optimization process.
int accelerator_num
number of utilized accelerators
A base class to determine the decomposition of an N-qubit unitary into a sequence of CNOT and U3 gate...
int num_threads
Store the number of OpenMP threads. (During the calculations OpenMP multithreading is turned off...
Class to store data of complex arrays and its properties.
Definition: matrix.h:38
void calc_decomposition_error(Matrix &decomposed_matrix)
Calculate the error of the decomposition according to the spectral norm of , where is the unitary pr...
int size() const
Call to get the number of the allocated elements.
void omp_set_num_threads(int num_threads)
Set the number of threads on runtime in MKL.
guess_type
Type definition of the types of the initial guess.
std::map< std::string, Config_Element > config
config metadata utilized during the optimization
virtual void start_decomposition()
Start the disentanglig process of the unitary.
Header file for the paralleized calculation of the cost function of the final optimization problem (s...
Matrix Umtx
The unitary to be decomposed.
Matrix copy()
Call to create a copy of the matrix.
Definition: matrix.cpp:105
void final_optimization()
final optimization procedure improving the accuracy of the decompositin when all the qubits were alre...
int qbit_num
number of qubits spanning the matrix of the operation
Definition: Gate.h:81
double decomposition_error
error of the final decomposition
Matrix_real optimized_parameters_mtx
The optimized parameters for the gates.
int omp_get_max_threads()
get the number of threads in MKL