Skip to main content

3.5.2 Eigen Usage on RVV

Last Version: 10/09/2025

Eigen is a high-performance C++ template library for linear algebra, matrix and vector operations, numerical analysis, and related algorithms.

  • It's a header-only library—no compilation required, just include the headers to use it.
  • SpacemiT RVV-enabled Eigen library is built on OpenBLAS.

Key Features

  • High Performance: Heavily optimized, with performance close to Fortran and C implementations
  • Easy to Use: Intuitive API design with operator overloading support
  • Header-Only: No compilation needed—just include the headers
  • Rich Functionality: Supports matrix operations, linear system solving, eigenvalue decomposition, and more

Basic Usage

Basic Includes and Namespace

#include <Eigen/Dense>
using namespace Eigen;

Vector Operations

#include <iostream>
#include <Eigen/Dense>

int main() {
// Create vectors
Vector3d v1(1, 2, 3); // 3-dimensional vector
VectorXd v2(5); // Dynamically sized vector
v2 << 1, 2, 3, 4, 5; // Initialize

// Vector operations
Vector3d v3 = v1 + Vector3d(1, 1, 1); // Vector addition
double dot_product = v1.dot(v3); // Dot product
Vector3d cross_product = v1.cross(v3); // Cross product
double norm = v1.norm(); // Vector magnitude

std::cout << "v1: " << v1.transpose() << std::endl;
std::cout << "Dot product: " << dot_product << std::endl;
std::cout << "Magnitude: " << norm << std::endl;

return 0;
}

Matrix Operations

#include <iostream>
#include <Eigen/Dense>

int main() {
// Create matrices
Matrix3d m1; // 3x3 matrix
m1 << 1, 2, 3,
4, 5, 6,
7, 8, 9;

MatrixXd m2(3, 4); // Dynamically sized matrix
m2 = MatrixXd::Random(3, 4); // Random matrix

// Special matrices
Matrix3d identity = Matrix3d::Identity(); // Identity matrix
Matrix3d zeros = Matrix3d::Zero(); // Zero matrix
Matrix3d ones = Matrix3d::Ones(); // Ones matrix

// Matrix operations
Matrix3d m3 = m1 + identity; // Matrix addition
Matrix3d m4 = m1 * m3; // Matrix multiplication
Matrix3d m5 = m1.transpose(); // Transpose

std::cout << "Matrix m1:\n" << m1 << std::endl;
std::cout << "Transpose of m1:\n" << m5 << std::endl;

return 0;
}

Matrix Decompositions

#include <iostream>
#include <Eigen/Dense>

int main() {
Matrix3d A;
A << 4, -2, 1,
-2, 4, -2,
1, -2, 4;

// LU decomposition
PartialPivLU<Matrix3d> lu(A);
Matrix3d L = lu.matrixLU().triangularView<Lower>();
Matrix3d U = lu.matrixLU().triangularView<Upper>();

// QR decomposition
HouseholderQR<Matrix3d> qr(A);
Matrix3d Q = qr.householderQ();
Matrix3d R = qr.matrixQR().triangularView<Upper>();

// Eigen decomposition
SelfAdjointEigenSolver<Matrix3d> eigen_solver(A);
Vector3d eigenvalues = eigen_solver.eigenvalues();
Matrix3d eigenvectors = eigen_solver.eigenvectors();

std::cout << "Eigenvalues:" << eigenvalues.transpose() << std::endl;
std::cout << "Eigenvectors:\n" << eigenvectors << std::endl;

return 0;
}

Linear System Solving

#include <iostream>
#include <Eigen/Dense>

int main() {
// Solve Ax = b
Matrix3d A;
A << 2, 1, 1,
1, 2, 1,
1, 1, 2;

Vector3d b(1, 2, 3);

// Method 1: Direct solving
Vector3d x1 = A.colPivHouseholderQr().solve(b);

// Method 2: LU decomposition
Vector3d x2 = A.partialPivLu().solve(b);

// Method 3: Cholesky decomposition (for symmetric positive definite matrices)
Vector3d x3 = A.llt().solve(b);

std::cout << "Solution x: " << x1.transpose() << std::endl;
std::cout << "Verify Ax = " << (A * x1).transpose() << std::endl;

return 0;
}

Geometric Transformations

#include <iostream>
#include <Eigen/Dense>
#include <Eigen/Geometry>

int main() {
// Rotation matrix
AngleAxisd rotation(M_PI/4, Vector3d::UnitZ()); // Rotate 45° around Z-axis
Matrix3d R = rotation.toRotationMatrix();

// Translation vector
Vector3d t(1, 2, 3);

// Homogeneous transformation matrix
Matrix4d T = Matrix4d::Identity();
T.block<3,3>(0,0) = R;
T.block<3,1>(0,3) = t;

// Transform point
Vector3d point(1, 0, 0);
Vector4d point_homo;
point_homo << point, 1;
Vector4d transformed = T * point_homo;

std::cout << "Original point: " << point.transpose() << std::endl;
std::cout << "Transformed point: " << transformed.head<3>().transpose() << std::endl;

return 0;
}

Dynamic Matrix Operations

#include <iostream>
#include <Eigen/Dense>

int main() {
// Dynamically sized matrix
int rows = 4, cols = 3;
MatrixXd dynamic_matrix(rows, cols);

// Fill matrix
for(int i = 0; i < rows; i++) {
for(int j = 0; j < cols; j++) {
dynamic_matrix(i, j) = i * cols + j + 1;
}
}

// Matrix slicing and block operations
MatrixXd block = dynamic_matrix.block(1, 1, 2, 2); // 2x2 block starting at (1,1)
VectorXd row = dynamic_matrix.row(0); // Row 0
VectorXd col = dynamic_matrix.col(1); // Column 1

std::cout << "Dynamic matrix:\n" << dynamic_matrix << std::endl;
std::cout << "2x2 block:\n" << block << std::endl;
std::cout << "Row 0: " << row.transpose() << std::endl;

return 0;
}

Compilation Methods