xref: /aosp_15_r20/external/eigen/doc/examples/make_circulant2.cpp (revision bf2c37156dfe67e5dfebd6d394bad8b2ab5804d4)
1*bf2c3715SXin Li #include <Eigen/Core>
2*bf2c3715SXin Li #include <iostream>
3*bf2c3715SXin Li 
4*bf2c3715SXin Li using namespace Eigen;
5*bf2c3715SXin Li 
6*bf2c3715SXin Li // [circulant_func]
7*bf2c3715SXin Li template<class ArgType>
8*bf2c3715SXin Li class circulant_functor {
9*bf2c3715SXin Li   const ArgType &m_vec;
10*bf2c3715SXin Li public:
circulant_functor(const ArgType & arg)11*bf2c3715SXin Li   circulant_functor(const ArgType& arg) : m_vec(arg) {}
12*bf2c3715SXin Li 
operator ()(Index row,Index col) const13*bf2c3715SXin Li   const typename ArgType::Scalar& operator() (Index row, Index col) const {
14*bf2c3715SXin Li     Index index = row - col;
15*bf2c3715SXin Li     if (index < 0) index += m_vec.size();
16*bf2c3715SXin Li     return m_vec(index);
17*bf2c3715SXin Li   }
18*bf2c3715SXin Li };
19*bf2c3715SXin Li // [circulant_func]
20*bf2c3715SXin Li 
21*bf2c3715SXin Li // [square]
22*bf2c3715SXin Li template<class ArgType>
23*bf2c3715SXin Li struct circulant_helper {
24*bf2c3715SXin Li   typedef Matrix<typename ArgType::Scalar,
25*bf2c3715SXin Li                  ArgType::SizeAtCompileTime,
26*bf2c3715SXin Li                  ArgType::SizeAtCompileTime,
27*bf2c3715SXin Li                  ColMajor,
28*bf2c3715SXin Li                  ArgType::MaxSizeAtCompileTime,
29*bf2c3715SXin Li                  ArgType::MaxSizeAtCompileTime> MatrixType;
30*bf2c3715SXin Li };
31*bf2c3715SXin Li // [square]
32*bf2c3715SXin Li 
33*bf2c3715SXin Li // [makeCirculant]
34*bf2c3715SXin Li template <class ArgType>
35*bf2c3715SXin Li CwiseNullaryOp<circulant_functor<ArgType>, typename circulant_helper<ArgType>::MatrixType>
makeCirculant(const Eigen::MatrixBase<ArgType> & arg)36*bf2c3715SXin Li makeCirculant(const Eigen::MatrixBase<ArgType>& arg)
37*bf2c3715SXin Li {
38*bf2c3715SXin Li   typedef typename circulant_helper<ArgType>::MatrixType MatrixType;
39*bf2c3715SXin Li   return MatrixType::NullaryExpr(arg.size(), arg.size(), circulant_functor<ArgType>(arg.derived()));
40*bf2c3715SXin Li }
41*bf2c3715SXin Li // [makeCirculant]
42*bf2c3715SXin Li 
43*bf2c3715SXin Li // [main]
main()44*bf2c3715SXin Li int main()
45*bf2c3715SXin Li {
46*bf2c3715SXin Li   Eigen::VectorXd vec(4);
47*bf2c3715SXin Li   vec << 1, 2, 4, 8;
48*bf2c3715SXin Li   Eigen::MatrixXd mat;
49*bf2c3715SXin Li   mat = makeCirculant(vec);
50*bf2c3715SXin Li   std::cout << mat << std::endl;
51*bf2c3715SXin Li }
52*bf2c3715SXin Li // [main]
53