mirror of
https://gitlab.com/libeigen/eigen.git
synced 2025-08-12 03:39:01 +08:00
Tutorial page 3: add more cwise operations, condense rest.
This commit is contained in:
parent
8e776c94c1
commit
140ad0908d
@ -7,7 +7,7 @@ namespace Eigen {
|
|||||||
\li \b Next: \ref TutorialBlockOperations
|
\li \b Next: \ref TutorialBlockOperations
|
||||||
|
|
||||||
This tutorial aims to provide an overview and explanations on how to use
|
This tutorial aims to provide an overview and explanations on how to use
|
||||||
Eigen's \link ArrayBase Array \endlink class
|
Eigen's Array class.
|
||||||
|
|
||||||
\b Table \b of \b contents
|
\b Table \b of \b contents
|
||||||
- \ref TutorialArrayClassIntro
|
- \ref TutorialArrayClassIntro
|
||||||
@ -15,6 +15,7 @@ Eigen's \link ArrayBase Array \endlink class
|
|||||||
- \ref TutorialArrayClassAccess
|
- \ref TutorialArrayClassAccess
|
||||||
- \ref TutorialArrayClassAddSub
|
- \ref TutorialArrayClassAddSub
|
||||||
- \ref TutorialArrayClassMult
|
- \ref TutorialArrayClassMult
|
||||||
|
- \ref TutorialArrayClassCwiseOther
|
||||||
- \ref TutorialArrayClassConvert
|
- \ref TutorialArrayClassConvert
|
||||||
|
|
||||||
\section TutorialArrayClassIntro What is the Array class?
|
\section TutorialArrayClassIntro What is the Array class?
|
||||||
@ -27,17 +28,17 @@ such as adding a constant to every coefficient in the array or multiplying two a
|
|||||||
|
|
||||||
\section TutorialArrayClassTypes Array types
|
\section TutorialArrayClassTypes Array types
|
||||||
Array is a class template taking the same template parameters as Matrix.
|
Array is a class template taking the same template parameters as Matrix.
|
||||||
As with Matrix, the first 3 template parameters are mandatory:
|
As with Matrix, the first three template parameters are mandatory:
|
||||||
\code
|
\code
|
||||||
Array<typename Scalar, int RowsAtCompileTime, int ColsAtCompileTime>
|
Array<typename Scalar, int RowsAtCompileTime, int ColsAtCompileTime>
|
||||||
\endcode
|
\endcode
|
||||||
And the last 3 template parameters are optional. Since this is exactly the same as for Matrix,
|
The last three template parameters are optional. Since this is exactly the same as for Matrix,
|
||||||
we won't reexplain it and just refer to \ref TutorialMatrixClass "this page".
|
we won't explain it again here and just refer to \ref TutorialMatrixClass.
|
||||||
|
|
||||||
Eigen also provides typedefs for some common cases, in a way that is similar to the Matrix typedefs
|
Eigen also provides typedefs for some common cases, in a way that is similar to the Matrix typedefs
|
||||||
but with some slight differences, as the word "array" is used for both 1-dimensional and 2-dimensional arrays.
|
but with some slight differences, as the word "array" is used for both 1-dimensional and 2-dimensional arrays.
|
||||||
We adopt that convention that typedefs of the form ArrayNt stand for 1-dimensional arrays, where N and t are
|
We adopt that convention that typedefs of the form ArrayNt stand for 1-dimensional arrays, where N and t are
|
||||||
as in the Matrix typedefs explained on \ref TutorialMatrixClass "this page". For 2-dimensional arrays, we
|
the size and the scalar type, as in the Matrix typedefs explained on \ref TutorialMatrixClass "this page". For 2-dimensional arrays, we
|
||||||
use typedefs of the form ArrayNNt. Some examples are shown in the following table:
|
use typedefs of the form ArrayNNt. Some examples are shown in the following table:
|
||||||
|
|
||||||
<table class="tutorial_code" align="center">
|
<table class="tutorial_code" align="center">
|
||||||
@ -71,69 +72,103 @@ use typedefs of the form ArrayNNt. Some examples are shown in the following tabl
|
|||||||
|
|
||||||
|
|
||||||
\section TutorialArrayClassAccess Accessing values inside an Array
|
\section TutorialArrayClassAccess Accessing values inside an Array
|
||||||
Write and read access to coefficients of an array expression is done in the same way as with matrix expressions.
|
|
||||||
For example:
|
|
||||||
|
|
||||||
\include Tutorial_ArrayClass_accessors.cpp
|
The parenthesis operator is overloaded to provide write and read access to the coefficients of an array, just as with matrices.
|
||||||
Output:
|
Furthermore, the \c << operator can be used to initialize arrays (via the comma initializer) or to print them.
|
||||||
\verbinclude Tutorial_ArrayClass_accessors.out
|
|
||||||
|
|
||||||
For more information about the comma initializer, refer to \ref TutorialAdvancedInitialization "this page".
|
<table class="tutorial_code"><tr><td>
|
||||||
|
Example: \include Tutorial_ArrayClass_accessors.cpp
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
Output: \verbinclude Tutorial_ArrayClass_accessors.out
|
||||||
|
</td></tr></table>
|
||||||
|
|
||||||
|
For more information about the comma initializer, see \ref TutorialAdvancedInitialization.
|
||||||
|
|
||||||
|
|
||||||
\section TutorialArrayClassAddSub Addition and substraction
|
\section TutorialArrayClassAddSub Addition and subtraction
|
||||||
|
|
||||||
|
Adding and subtracting two arrays is the same as for matrices.
|
||||||
|
The operation is valid if both arrays have the same size, and the addition or subtraction is done coefficient-wise.
|
||||||
|
|
||||||
|
Arrays also support expressions of the form <tt>array + scalar</tt> which add a scalar to each coefficient in the array.
|
||||||
|
This provides a functionality that is not directly available for Matrix objects.
|
||||||
|
|
||||||
|
<table class="tutorial_code"><tr><td>
|
||||||
|
Example: \include Tutorial_ArrayClass_addition.cpp
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
Output: \verbinclude Tutorial_ArrayClass_addition.out
|
||||||
|
</td></tr></table>
|
||||||
|
|
||||||
|
|
||||||
Adding and substracting two arrays has the same result as for Matrices.
|
\section TutorialArrayClassMult Array multiplication
|
||||||
This is valid as long as both arrays have the same sizes:
|
|
||||||
|
|
||||||
\include Tutorial_ArrayClass_addition.cpp
|
|
||||||
Output:
|
|
||||||
\verbinclude Tutorial_ArrayClass_addition.out
|
|
||||||
|
|
||||||
It is also allowed to add a scalar to each coefficient in an Array,
|
|
||||||
providing a functionality that was not available for Matrix objects:
|
|
||||||
|
|
||||||
\include Tutorial_ArrayClass_addition_scalar.cpp
|
|
||||||
Output:
|
|
||||||
\verbinclude Tutorial_ArrayClass_addition_scalar.out
|
|
||||||
|
|
||||||
|
|
||||||
\subsection TutorialArrayClassMult Array multiplication
|
|
||||||
|
|
||||||
First of all, of course you can multiply an array by a scalar, this works in the same way as matrices. Where arrays
|
First of all, of course you can multiply an array by a scalar, this works in the same way as matrices. Where arrays
|
||||||
are fundamentally different from matrices, is when you multiply two arrays together. While Matrices interprete
|
are fundamentally different from matrices, is when you multiply two together. Matrices interpret
|
||||||
multiplication as matrix product, arrays interprete multiplication as coefficient-wise product. For example:
|
multiplication as the matrix product and arrays interpret multiplication as the coefficient-wise product. Thus, two
|
||||||
|
arrays can be multiplied if they have the same size.
|
||||||
|
|
||||||
\include Tutorial_ArrayClass_mult.cpp
|
<table class="tutorial_code"><tr><td>
|
||||||
Output:
|
Example: \include Tutorial_ArrayClass_mult.cpp
|
||||||
\verbinclude Tutorial_ArrayClass_mult.out
|
</td>
|
||||||
|
<td>
|
||||||
|
Output: \verbinclude Tutorial_ArrayClass_mult.out
|
||||||
|
</td></tr></table>
|
||||||
|
|
||||||
|
|
||||||
|
\section TutorialArrayClassCwiseOther Other coefficient-wise operations
|
||||||
|
|
||||||
|
The Array class defined other coefficient-wise operations besides the addition, subtraction and multiplication
|
||||||
|
operators described about. For example, the \link ArrayBase::abs() .abs() \endlink method takes the absolute
|
||||||
|
value of each coefficient, while \link ArrayBase::sqrt() .sqrt() \endlink computes the square root of the
|
||||||
|
coefficients. If you have two arrays of the same size, you can call \link ArrayBase::min() .min() \endlink to
|
||||||
|
construct the array whose coefficients are the minimum of the corresponding coefficients of the two given
|
||||||
|
arrays. These operations are illustrated in the following example.
|
||||||
|
|
||||||
|
<table class="tutorial_code"><tr><td>
|
||||||
|
Example: \include Tutorial_ArrayClass_cwise_other.cpp
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
Output: \verbinclude Tutorial_ArrayClass_cwise_other.out
|
||||||
|
</td></tr></table>
|
||||||
|
|
||||||
|
More coefficient-wise operations can be found in the \ref QuickRefPage.
|
||||||
|
|
||||||
|
|
||||||
\section TutorialArrayClassConvert Converting between array and matrix expressions
|
\section TutorialArrayClassConvert Converting between array and matrix expressions
|
||||||
|
|
||||||
It is possible to wrap a matrix expression as an array expression and conversely. This gives access to all operations
|
When should you use objects of the Matrix class and when should you use objects of the Array class? You cannot
|
||||||
regardless of the choice of declaring objects as arrays or as matrices.
|
apply Matrix operations on arrays, or Array operations on matrices. Thus, if you need to do linear algebraic
|
||||||
|
operations such as matrix multiplication, then you should use matrices; if you need to do coefficient-wise
|
||||||
|
operations, then you should use arrays. However, sometimes it is not that simple, but you need to use both
|
||||||
|
Matrix and Array operations. In that case, you need to convert a matrix to an array or reversely. This gives
|
||||||
|
access to all operations regardless of the choice of declaring objects as arrays or as matrices.
|
||||||
|
|
||||||
\link MatrixBase Matrix expressions \endlink have a \link MatrixBase::array() .array() \endlink method that
|
\link MatrixBase Matrix expressions \endlink have an \link MatrixBase::array() .array() \endlink method that
|
||||||
'converts' them into \link ArrayBase array expressions\endlink, so that coefficient-wise operations
|
'converts' them into \link ArrayBase array expressions\endlink, so that coefficient-wise operations
|
||||||
can be applied easily. Conversely, \link ArrayBase array expressions \endlink
|
can be applied easily. Conversely, \link ArrayBase array expressions \endlink
|
||||||
have a \link ArrayBase::matrix() .matrix() \endlink method. As with all Eigen expression abstractions,
|
have a \link ArrayBase::matrix() .matrix() \endlink method. As with all Eigen expression abstractions,
|
||||||
this doesn't have any runtime cost (provided that you let your compiler optimize).
|
this doesn't have any runtime cost (provided that you let your compiler optimize).
|
||||||
|
|
||||||
Both \link MatrixBase::array() .array() \endlink and \link ArrayBase::matrix() .matrix() \endlink
|
Both \link MatrixBase::array() .array() \endlink and \link ArrayBase::matrix() .matrix() \endlink
|
||||||
can be used as rvalues and as lvalues.
|
can be used as rvalues and as lvalues.
|
||||||
|
|
||||||
Mixing matrices and arrays in an expression is forbidden with Eigen. However,
|
Mixing matrices and arrays in an expression is forbidden with Eigen. For instance, you cannot add a amtrix and
|
||||||
|
array directly; the operands of a \c + operator should either both be matrices or both be arrays. However,
|
||||||
it is easy to convert from one to the other with \link MatrixBase::array() .array() \endlink and
|
it is easy to convert from one to the other with \link MatrixBase::array() .array() \endlink and
|
||||||
\link ArrayBase::matrix() .matrix() \endlink.
|
\link ArrayBase::matrix() .matrix()\endlink. The exception to this rule is the assignment operator: it is
|
||||||
|
allowed to assign a matrix expression to an array variable, or to assign an array expression to a matrix
|
||||||
|
variable.
|
||||||
|
|
||||||
On the other hand, assigning a matrix (resp. array) expression to an array (resp. matrix) expression is allowed.
|
The following example shows how to use array operations on a Matrix object by employing the
|
||||||
|
\link MatrixBase::array() .array() \endlink method. For example, the statement
|
||||||
|
<tt>result = m.array() * n.array()</tt> takes two matrices \c m and \c n, converts them both to an array, uses
|
||||||
|
* to multiply them coefficient-wise and assigns the result to the matrix variable \c result (this is legal
|
||||||
|
because Eigen allows assigning array expressions to matrix variables).
|
||||||
|
|
||||||
\subsection TutorialArrayClassInteropMatrix Matrix to array example
|
As a matter of fact, this usage case is so common that Eigen provides a \link MatrixBase::cwiseProduct()
|
||||||
The following example shows how to use array operations on a Matrix object by employing
|
.cwiseProduct() \endlink method for matrices to compute the coefficient-wise product. This is also shown in
|
||||||
the \link MatrixBase::array() .array() \endlink method:
|
the example program.
|
||||||
|
|
||||||
<table class="tutorial_code"><tr><td>
|
<table class="tutorial_code"><tr><td>
|
||||||
\include Tutorial_ArrayClass_interop_matrix.cpp
|
\include Tutorial_ArrayClass_interop_matrix.cpp
|
||||||
@ -143,21 +178,13 @@ Output:
|
|||||||
\verbinclude Tutorial_ArrayClass_interop_matrix.out
|
\verbinclude Tutorial_ArrayClass_interop_matrix.out
|
||||||
</td></tr></table>
|
</td></tr></table>
|
||||||
|
|
||||||
|
Similarly, if \c array1 and \c array2 are arrays, then the expression <tt>array1.matrix() * array2.matrix()</tt>
|
||||||
|
computes their matrix product.
|
||||||
|
|
||||||
\subsection TutorialArrayClassInteropArray Array to matrix example
|
Here is a more advanced example. The expression <tt>(m.array() + 4).matrix() * m</tt> adds 4 to every
|
||||||
The following example shows how to use matrix operations with an Array
|
coefficient in the matrix \c m and then computes the matrix product of the result with \c m. Similarly, the
|
||||||
object by employing the \link ArrayBase::matrix() .matrix() \endlink method:
|
expression <tt>(m.array() * n.array()).matrix() * m</tt> computes the coefficient-wise product of the matrices
|
||||||
|
\c m and \c n and then the matrix product of the result with \c m.
|
||||||
<table class="tutorial_code"><tr><td>
|
|
||||||
\include Tutorial_ArrayClass_interop_array.cpp
|
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
Output:
|
|
||||||
\verbinclude Tutorial_ArrayClass_interop_array.out
|
|
||||||
</td></tr></table>
|
|
||||||
|
|
||||||
\subsection TutorialArrayClassInteropCombination Example with combinations of .array() and .matrix()
|
|
||||||
Here is a more advanced example:
|
|
||||||
|
|
||||||
<table class="tutorial_code"><tr><td>
|
<table class="tutorial_code"><tr><td>
|
||||||
\include Tutorial_ArrayClass_interop.cpp
|
\include Tutorial_ArrayClass_interop.cpp
|
||||||
|
@ -10,7 +10,7 @@ int main()
|
|||||||
|
|
||||||
// assign some values coefficient by coefficient
|
// assign some values coefficient by coefficient
|
||||||
m(0,0) = 1.0; m(0,1) = 2.0;
|
m(0,0) = 1.0; m(0,1) = 2.0;
|
||||||
m(1,0) = 3.0; m(1,1) = 4.0;
|
m(1,0) = 3.0; m(1,1) = m(0,1) + m(1,0);
|
||||||
|
|
||||||
// print values to standard output
|
// print values to standard output
|
||||||
cout << m << endl << endl;
|
cout << m << endl << endl;
|
||||||
|
@ -8,15 +8,16 @@ int main()
|
|||||||
{
|
{
|
||||||
ArrayXXf a(3,3);
|
ArrayXXf a(3,3);
|
||||||
ArrayXXf b(3,3);
|
ArrayXXf b(3,3);
|
||||||
|
|
||||||
a << 1,2,3,
|
a << 1,2,3,
|
||||||
4,5,6,
|
4,5,6,
|
||||||
7,8,9;
|
7,8,9;
|
||||||
|
|
||||||
b << 1,2,3,
|
b << 1,2,3,
|
||||||
1,2,3,
|
1,2,3,
|
||||||
1,2,3;
|
1,2,3;
|
||||||
|
|
||||||
cout << "a + b = " << endl
|
// Adding two arrays
|
||||||
<< a + b << endl;
|
cout << "a + b = " << endl << a + b << endl << endl;
|
||||||
|
|
||||||
|
// Subtracting a scalar from an array
|
||||||
|
cout << "a - 2 = " << endl << a - 2 << endl;
|
||||||
}
|
}
|
||||||
|
@ -1,17 +0,0 @@
|
|||||||
#include <Eigen/Dense>
|
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
using namespace Eigen;
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
ArrayXXf a(3,3);
|
|
||||||
|
|
||||||
a << 1,2,3,
|
|
||||||
4,5,6,
|
|
||||||
7,8,9;
|
|
||||||
|
|
||||||
cout << "a + 2 = " << endl
|
|
||||||
<< a + 2 << endl;
|
|
||||||
}
|
|
19
doc/examples/Tutorial_ArrayClass_cwise_other.cpp
Normal file
19
doc/examples/Tutorial_ArrayClass_cwise_other.cpp
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
#include <Eigen/Dense>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
using namespace Eigen;
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
ArrayXf a = ArrayXf::Random(5);
|
||||||
|
a *= 2;
|
||||||
|
cout << "a =" << endl
|
||||||
|
<< a << endl;
|
||||||
|
cout << "a.abs() =" << endl
|
||||||
|
<< a.abs() << endl;
|
||||||
|
cout << "a.abs().sqrt() =" << endl
|
||||||
|
<< a.abs().sqrt() << endl;
|
||||||
|
cout << "a.min(a.abs().sqrt()) =" << endl
|
||||||
|
<< a.min(a.abs().sqrt()) << endl;
|
||||||
|
}
|
@ -8,31 +8,15 @@ int main()
|
|||||||
{
|
{
|
||||||
MatrixXf m(2,2);
|
MatrixXf m(2,2);
|
||||||
MatrixXf n(2,2);
|
MatrixXf n(2,2);
|
||||||
|
|
||||||
MatrixXf result(2,2);
|
MatrixXf result(2,2);
|
||||||
|
|
||||||
//initialize matrices
|
|
||||||
m << 1,2,
|
m << 1,2,
|
||||||
3,4;
|
3,4;
|
||||||
|
|
||||||
n << 5,6,
|
n << 5,6,
|
||||||
7,8;
|
7,8;
|
||||||
|
|
||||||
// mix of array and matrix operations
|
|
||||||
// first coefficient-wise addition
|
|
||||||
// then the result is used with matrix multiplication
|
|
||||||
result = (m.array() + 4).matrix() * m;
|
result = (m.array() + 4).matrix() * m;
|
||||||
|
cout << "-- Combination 1: --" << endl << result << endl << endl;
|
||||||
cout << "-- Combination 1: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
|
|
||||||
|
|
||||||
// mix of array and matrix operations
|
|
||||||
// first coefficient-wise multiplication
|
|
||||||
// then the result is used with matrix multiplication
|
|
||||||
result = (m.array() * n.array()).matrix() * m;
|
result = (m.array() * n.array()).matrix() * m;
|
||||||
|
cout << "-- Combination 2: --" << endl << result << endl << endl;
|
||||||
cout << "-- Combination 2: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,34 +0,0 @@
|
|||||||
#include <Eigen/Dense>
|
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
using namespace Eigen;
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
ArrayXXf m(2,2);
|
|
||||||
ArrayXXf n(2,2);
|
|
||||||
|
|
||||||
ArrayXXf result(2,2);
|
|
||||||
|
|
||||||
//initialize arrays
|
|
||||||
m << 1,2,
|
|
||||||
3,4;
|
|
||||||
|
|
||||||
n << 5,6,
|
|
||||||
7,8;
|
|
||||||
|
|
||||||
|
|
||||||
// --> array multiplication
|
|
||||||
result = m * n;
|
|
||||||
|
|
||||||
cout << "-- Array m*n: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
|
|
||||||
|
|
||||||
// --> Matrix multiplication
|
|
||||||
result = m.matrix() * n.matrix();
|
|
||||||
|
|
||||||
cout << "-- Matrix m*n: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
}
|
|
@ -8,34 +8,19 @@ int main()
|
|||||||
{
|
{
|
||||||
MatrixXf m(2,2);
|
MatrixXf m(2,2);
|
||||||
MatrixXf n(2,2);
|
MatrixXf n(2,2);
|
||||||
|
|
||||||
MatrixXf result(2,2);
|
MatrixXf result(2,2);
|
||||||
|
|
||||||
//initialize matrices
|
|
||||||
m << 1,2,
|
m << 1,2,
|
||||||
3,4;
|
3,4;
|
||||||
|
|
||||||
n << 5,6,
|
n << 5,6,
|
||||||
7,8;
|
7,8;
|
||||||
|
|
||||||
|
|
||||||
// --> matrix multiplication
|
|
||||||
result = m * n;
|
result = m * n;
|
||||||
|
cout << "-- Matrix m*n: --" << endl << result << endl << endl;
|
||||||
cout << "-- Matrix m*n: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
|
|
||||||
|
|
||||||
// --> coeff-wise multiplication
|
|
||||||
result = m.array() * n.array();
|
result = m.array() * n.array();
|
||||||
|
cout << "-- Array m*n: --" << endl << result << endl << endl;
|
||||||
cout << "-- Array m*n: --" << endl
|
result = m.cwiseProduct(n);
|
||||||
<< result << endl << endl;
|
cout << "-- With cwiseProduct: --" << endl << result << endl << endl;
|
||||||
|
|
||||||
|
|
||||||
// ->> coeff-wise addition of a scalar
|
|
||||||
result = m.array() + 4;
|
result = m.array() + 4;
|
||||||
|
cout << "-- Array m + 4: --" << endl << result << endl << endl;
|
||||||
cout << "-- Array m + 4: --" << endl
|
|
||||||
<< result << endl << endl;
|
|
||||||
}
|
}
|
||||||
|
@ -8,13 +8,9 @@ int main()
|
|||||||
{
|
{
|
||||||
ArrayXXf a(2,2);
|
ArrayXXf a(2,2);
|
||||||
ArrayXXf b(2,2);
|
ArrayXXf b(2,2);
|
||||||
|
|
||||||
a << 1,2,
|
a << 1,2,
|
||||||
3,4;
|
3,4;
|
||||||
|
|
||||||
b << 5,6,
|
b << 5,6,
|
||||||
7,8;
|
7,8;
|
||||||
|
cout << "a * b = " << endl << a * b << endl;
|
||||||
cout << "a * b = " << endl
|
|
||||||
<< a * b << endl;
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user