27 #ifndef INTERNAL_UTIL_H_
28 #define INTERNAL_UTIL_H_
45 for (
idx i = 0; i < numdims; ++i)
47 result[numdims - i - 1] = n % (dims[numdims - i - 1]);
48 n /= (dims[numdims - i - 1]);
64 part_prod[numdims - 1] = 1;
65 for (
idx i = 1; i < numdims; ++i)
67 part_prod[numdims - i - 1] =
68 part_prod[numdims - i] * dims[numdims - i];
69 result += midx[numdims - i - 1] * part_prod[numdims - i - 1];
72 return result + midx[numdims - 1];
76 template<
typename Derived>
81 return rA.rows() == rA.cols();
85 template<
typename Derived>
90 return rA.rows() == 1 || rA.cols() == 1;
94 template<
typename Derived>
99 return rA.rows() == 1;
103 template<
typename Derived>
108 return rA.cols() == 1;
115 return x.size() != 0;
121 if (dims.size() == 0)
124 return std::find_if(std::begin(dims), std::end(dims),
125 [dims](
idx i) ->
bool
127 if (i == 0)
return true;
129 }) == std::end(dims);
134 template<
typename Derived>
136 const Eigen::MatrixBase<Derived>& A)
140 idx proddim = std::accumulate(std::begin(dims), std::end(dims),
141 static_cast<idx>(1), std::multiplies<idx>());
143 return proddim ==
static_cast<idx>(rA.rows());
147 template<
typename Derived>
149 const Eigen::MatrixBase<Derived>& V)
153 idx proddim = std::accumulate(std::begin(dims), std::end(dims),
154 static_cast<idx>(1), std::multiplies<idx>());
156 return proddim ==
static_cast<idx>(rV.rows());
160 template<
typename Derived>
162 const Eigen::MatrixBase<Derived>& V)
166 idx proddim = std::accumulate(std::begin(dims), std::end(dims),
167 static_cast<idx>(1), std::multiplies<idx>());;
169 return proddim ==
static_cast<idx>(rV.cols());
184 const std::vector <idx>& dims)
191 if (subsys.size() > dims.size())
195 std::vector <idx> subsyssort = subsys;
196 std::sort(std::begin(subsyssort), std::end(subsyssort));
199 if (std::unique(std::begin(subsyssort), std::end(subsyssort))
200 != std::end(subsyssort))
204 return std::find_if(std::begin(subsyssort), std::end(subsyssort),
205 [dims](
idx i) ->
bool
207 return i > dims.size() - 1;
208 }) == std::end(subsyssort);
212 template<
typename Derived>
217 return rA.rows() == 2 && rA.cols() == 2;
221 template<
typename Derived>
226 return rV.rows() == 2 && rV.cols() == 1;
230 template<
typename Derived>
235 return rV.rows() == 1 && rV.cols() == 2;
239 template<
typename Derived>
244 return (rV.rows() == 1 && rV.cols() == 2) ||
245 (rV.rows() == 2 && rV.cols() == 1);
252 if (perm.size() == 0)
255 std::vector <idx> ordered(perm.size());
256 std::iota(std::begin(ordered), std::end(ordered), 0);
258 return std::is_permutation(std::begin(ordered), std::end(ordered),
264 template<
typename Derived1,
typename Derived2>
266 const Eigen::MatrixBase<Derived2>& B)
274 if (!std::is_same<
typename Derived1::Scalar,
275 typename Derived2::Scalar>::value)
286 idx Acols =
static_cast<idx>(rA.cols());
287 idx Arows =
static_cast<idx>(rA.rows());
288 idx Bcols =
static_cast<idx>(rB.cols());
289 idx Brows =
static_cast<idx>(rB.rows());
292 result.resize(Arows * Brows, Acols * Bcols);
294 #pragma omp parallel for collapse(2)
295 for (
idx j = 0; j < Acols; ++j)
296 for (
idx i = 0; i < Arows; ++i)
297 result.block(i * Brows, j * Bcols, Brows, Bcols) = rA(i, j) * rB;
304 template<
typename Derived1,
typename Derived2>
306 const Eigen::MatrixBase<Derived1>& A,
307 const Eigen::MatrixBase<Derived2>& B)
315 if (!std::is_same<
typename Derived1::Scalar,
316 typename Derived2::Scalar>::value)
327 idx Acols =
static_cast<idx>(rA.cols());
328 idx Arows =
static_cast<idx>(rA.rows());
329 idx Bcols =
static_cast<idx>(rB.cols());
330 idx Brows =
static_cast<idx>(rB.rows());
336 result.block(0, 0, Arows, Acols) = rA;
337 result.block(Arows, Acols, Brows, Bcols) = rB;
350 template<
typename T,
typename First,
typename ... Args>
353 v.emplace_back(std::forward<First>(first));
bool _check_cvector(const Eigen::MatrixBase< Derived > &A)
Definition: util.h:104
bool _check_qubit_cvector(const Eigen::MatrixBase< Derived > &V) noexcept
Definition: util.h:222
constexpr idx maxn
Maximum number of allowed qu(d)its (subsystems)
Definition: constants.h:82
bool _check_subsys_match_dims(const std::vector< idx > &subsys, const std::vector< idx > &dims)
Definition: util.h:183
bool _check_dims_match_mat(const std::vector< idx > &dims, const Eigen::MatrixBase< Derived > &A)
Definition: util.h:135
bool _check_dims_match_cvect(const std::vector< idx > &dims, const Eigen::MatrixBase< Derived > &V)
Definition: util.h:148
dyn_mat< typename Derived1::Scalar > _kron2(const Eigen::MatrixBase< Derived1 > &A, const Eigen::MatrixBase< Derived2 > &B)
Definition: util.h:265
Eigen::Matrix< Scalar, Eigen::Dynamic, Eigen::Dynamic > dyn_mat
Dynamic Eigen matrix over the field specified by Scalar.
Definition: types.h:84
bool _check_vector(const Eigen::MatrixBase< Derived > &A)
Definition: util.h:86
Quantum++ main namespace.
Definition: codes.h:30
bool _check_dims_match_rvect(const std::vector< idx > &dims, const Eigen::MatrixBase< Derived > &V)
Definition: util.h:161
bool _check_square_mat(const Eigen::MatrixBase< Derived > &A)
Definition: util.h:77
bool _check_rvector(const Eigen::MatrixBase< Derived > &A)
Definition: util.h:95
bool _check_qubit_matrix(const Eigen::MatrixBase< Derived > &A) noexcept
Definition: util.h:213
bool _check_perm(const std::vector< idx > &perm)
Definition: util.h:250
idx _multiidx2n(const idx *midx, idx numdims, const idx *dims) noexcept
Definition: util.h:54
Generates custom exceptions, used when validating function parameters.
Definition: exception.h:39
void variadic_vector_emplace(std::vector< T > &)
Definition: util.h:345
bool _check_nonzero_size(const T &x) noexcept
Definition: util.h:113
dyn_mat< typename Derived1::Scalar > _dirsum2(const Eigen::MatrixBase< Derived1 > &A, const Eigen::MatrixBase< Derived2 > &B)
Definition: util.h:305
bool _check_qubit_vector(const Eigen::MatrixBase< Derived > &V) noexcept
Definition: util.h:240
void _n2multiidx(idx n, idx numdims, const idx *dims, idx *result) noexcept
Definition: util.h:41
std::size_t idx
Non-negative integer index.
Definition: types.h:36
bool _check_dims(const std::vector< idx > &dims)
Definition: util.h:119
bool _check_eq_dims(const std::vector< idx > &dims, idx dim) noexcept
Definition: util.h:173
bool _check_qubit_rvector(const Eigen::MatrixBase< Derived > &V) noexcept
Definition: util.h:231