| /* |
| * $Id: usage.dox,v 1.14 2004/07/03 17:09:23 opetzold Exp $ |
| */ |
| |
| /** |
| \page usage Usage |
| |
| <p>Contents:</p> |
| -# \ref include |
| -# \ref construct |
| -# \ref c_arrays |
| -# \ref compare |
| -# \ref pod |
| -# \ref stl |
| -# \ref matrix_access |
| -# \ref expr_print |
| |
| |
| |
| |
| \section include Include files |
| |
| The Tiny %Vector and %Matrix template library has many include files spread |
| throughout the %tvmet include directory. As a user, you need only include |
| <tt><%tvmet/Vector></tt> for vector operations and/or |
| <tt><%tvmet/Matrix></tt> for matrix operations. |
| |
| \par Example: |
| \code |
| #include <tvmet/Matrix.h> |
| #include <tvmet/Vector.h> |
| |
| using namespace tvmet; |
| \endcode |
| |
| Simple, isn't it? Don't forget to use the namespace tvmet, but keep in mind |
| that using the using directive inside headers will pollute the namespace. If |
| you write this in a header file, the namespace for all subsequent header |
| files (those which include the one you're writing) will also be polluted. |
| (This is not a %tvmet specific phenomenon.) Therefore, write the using |
| statement in the C++ file. |
| |
| |
| |
| |
| |
| \section construct Construction and Initializing |
| |
| Due to the nature of |
| <a href=http://extreme.indiana.edu/~tveldhui/papers/Expression-Templates/exprtmpl.html> |
| Expression Templates</a> (ET) you can't write code like |
| |
| \par Example: |
| \code |
| tvmet::Vector<double, 3> v1(1,2,3); // OK |
| tvmet::Vector<double, 3> v2 = v1; // not possible |
| \endcode |
| |
| The operator= function assigns an expression to the Vector which means that |
| the object must be constructed before you may assign something to it. The |
| solution is to write this as: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Vector<double, 3> v1(1,2,3); |
| Vector<double, 3> v2; // construct the Vector<T,Sz> object at first |
| v2 = v1; // ... and assign the contents of v1 to v2 |
| Vector<double, 3> v3(v1); // ... or simple use the copy constructor |
| |
| std::cout << v3 << std::endl; |
| \endcode |
| |
| since the object v2 needs to be constructed before the object's operator=() |
| can be called. |
| |
| The same rule applies to the Matrix class. You can only assign vectors and |
| matrices of the same dimension or you will get a compile error. This also |
| applies to the argument list for the constructor of the classes. |
| |
| Initializing can be done as shown above or by using a comma separated list: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Matrix<double, 3, 2> m1; // yes, non-square matrices are possible as well |
| m1 = 1, 4, |
| 2, 5, |
| 3, 6; |
| \endcode |
| |
| Matrix element initialization always performed column wise! If the length |
| of the comma separated list is longer than the storage size, you will get |
| a compile time error. (tvmet is designed to prevent this -- it will prevent |
| you from accidentally overwriting memory which does not belong to the |
| matrix you are initializing.) You can use a comma separated list to |
| initialize vectors as well. |
| |
| If you want a clean (zero-valued) vector or matrix you can simple write: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Vector<double, 3> v4(0); |
| Matrix<double, 3, 4> m2(0); |
| \endcode |
| |
| All elements of v4 and m2 are initialized with zero (or whatever value you |
| provide at construction time). Keep in mind that the uninitialized %Matrix |
| and %Vector classes will have random data when the are created (since they |
| use a static array for internal storage) unless you initialize them! |
| |
| Another way to initialize a vector or matrix follows: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Vector<double, 3> v5(1,2,3); |
| Vector<double, 3> v6(v5); |
| Vector<double, 3> v7(v5+v6); |
| \endcode |
| |
| This is useful for temporary results. The result will be immediately |
| assigned to the new vector elements using the expression passed to the |
| constructor. |
| |
| Yet another way of initializing a vector or matrix is similar to the above. |
| We assign an expression to it: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Matrix<double, 3, 3> m3, m4, m5; |
| m3 = 1, 2, 3, |
| 4, 5, 6, |
| 7, 8, 9; |
| m4 = m3; |
| m5 = m3 + m4; |
| \endcode |
| |
| If you have your data inside arrays you can use tvmet's iterator interface |
| to initialize a vector or matrix with it: |
| |
| \par Example: |
| \code |
| T data[] = { 1,4,7, |
| 2,5,8, |
| 3,6,9 }; |
| |
| std::size_t sz = sizeof(data)/sizeof(T); |
| T* first = data; |
| T* last = data + sz; |
| |
| tvmet::Matrix<double, 3, 3> m(first, last); |
| \endcode |
| |
| The data will be copied into the matrix itself. When the constructor has |
| finished, there will be no stored reference to the array pointer. |
| |
| Starting with tvmet release 1.6.0 you can create an identity matrix |
| simply by using the function identity(). Note, we have to specify the |
| matrix type, since ADL can't work here. |
| |
| \par Example: |
| \code |
| typedef Matrix<double,3,3> matrix_type; |
| ... |
| matrix_type E( identity<matrix_type>() ); |
| \endcode |
| |
| |
| |
| |
| \section c_arrays Use of C style Arrays with tvmet |
| |
| Sometimes you have some data arranged in a C style array for matrices |
| and vectors. As with tvmet release 1.6.0 you can wrap an expression |
| around using the functions vector_ref(const T* mem) and |
| matrix_ref(const T* mem) where mem is the pointer to the C array. |
| |
| The returned expressions (XprVector or XprMatrix) can be used |
| as usual like tvmet's vectors and matrices. This means, you |
| can use all mathematical functions on it. |
| |
| \par Example: |
| \code |
| static float lhs[3][3] = { |
| {-1, 0, 1}, { 1, 0, 1}, {-1, 0, -1} |
| }; |
| static float rhs[3][3] = { |
| { 0, 1, 1}, { 0, 1, -1}, { 0, -1, 1} |
| }; |
| ... |
| |
| typedef Matrix<float, 3, 3> matrix_type; |
| |
| matrix_type M( prod(matrix_ref<float, 3, 3>(&lhs[0][0]), |
| matrix_ref<float, 3, 3>(&rhs[0][0])) ); |
| \endcode |
| |
| This allows to initialize tvmet's vectors and matrices by |
| an alternative way as described at \ref construct. |
| |
| |
| \section compare Compare Vectors and Matrices |
| |
| If you expect to find global comparison operators for comparing Vectors |
| and Matrices, you are right -- these are provided. But, the return |
| value probably isn't what you expect: a boolean value. Instead, the operator |
| returns an expression (e.g. XprVector<>). The contents of this expression |
| type is a element wise logical operation (depends on the given operator |
| like ==, <, >, etc...)! To get a boolean value you need to evaluate the |
| expression using all_elements() or any_elements(), as follows: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| using namespace std; |
| |
| Vector<double, 3> v1, v2, bv; |
| |
| v1 = 1,2,3; |
| v2 = 1,3,3; |
| |
| bv = v1 == v2; |
| |
| cout << bv << endl; |
| cout << "v1 == v2 is " |
| << ( all_elements( v1 == v2 ) ? "true" : "false" ) |
| << endl; |
| \endcode |
| |
| This gives |
| |
| \par [continued] |
| \code |
| Vector<d, 3>[1, 0, 1] |
| v1 == v2 is false |
| \endcode |
| |
| The reason for this is the element wise operation on all elements (for both |
| Vectors and Matrices). Comparing two vectors will result in a "boolean Vector" |
| expression. Using all_elements/any_elements evaluates the result into a |
| single boolean by repeatedly applying the comparison for each element. |
| |
| An other example on comparing is shown below: |
| |
| \par Example: |
| \code |
| if(all_elements(X == Y)) { cout << "matrices are identical" << endl; } |
| if(any_elements(X == Y)) { cout << "at least one element is equal" << endl; } |
| if(any_elements(X != Y)) { cout << "not all elements are equal" << endl; } |
| \endcode |
| |
| %tvmet prior release 1.2.1 did have a boolean version eval for comparing. |
| The functional and semantic meaning were not clear at all. Therefore I |
| decided to remove it. |
| |
| \sa \ref operators |
| |
| |
| |
| |
| |
| \section pod Data Types like std::complex<> |
| |
| As we can see above we can use POD (plain old data) types like <tt>double</tt> and |
| <tt>int</tt> as data type of a %Vector or %Matrix. However, we are not limited to |
| this - we can use e.g. <tt>std::complex<></tt> as well: |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| Vector<std::complex<double>,3> v1, v2; |
| Matrix<std::complex<double>,3,3> m1; |
| \endcode |
| |
| And operate on these... |
| |
| \par [continued] |
| \code |
| v1 = 1,2,3; |
| m1 = 1,4,7, |
| 2,5,8, |
| 3,6,9; |
| v2 = m1 * v1; |
| \endcode |
| |
| Be careful. <tt>std::complex<></tt> isn't tested well on regression tests. |
| |
| |
| |
| |
| \section stl STL support |
| |
| Since version 0.2.0 %tvmet has supported an iterator interface conform to |
| the STL and since version 0.5.0 reverse STL iterators have been supported, |
| too. |
| |
| With these, you can mix the %tvmet Vector and Matrix containers with the |
| STL algorithms. |
| |
| For example, if you don't like %tvmet's ostream operator, you can create |
| your own implementation like this: |
| |
| \par Example: |
| \code |
| tvmet::Vector<double, 6> v(1,2,3,4,5,6); |
| std::cout << v << std::endl; |
| |
| std::cout << "The Vector is:" << std::endl; |
| std::copy(v.begin(), v.end(), std::ostream_iterator<double>(std::cout, "\n")); |
| \endcode |
| |
| Or, you create a random matrix and print it as shown here: |
| |
| \par Example: |
| \code |
| tvmet::Matrix<double,6,6> m; |
| |
| std::generate(m.begin(), m.end(), rand); |
| std::cout << m << std::endl; |
| \endcode |
| |
| |
| |
| |
| |
| \section matrix_access Matrix access by rows and columns |
| |
| If you need a specific row or column of a given matrix you can get access to |
| it by using the functions row and col. They will return an XprVector<T>. |
| Unfortunately, you do not get any write access to the vector elements - only |
| reading is permitted due to the expression template concept used here. For |
| write access, you have to use matrix indexing with the parentheses operator. |
| |
| \par Example: |
| \code |
| using namespace tvmet; |
| |
| typedef Matrix<double 5, 3> matrix_type; |
| typedef Vector<double, 5> matrix_rowvector; |
| typedef Vector<double, 3> matrix_colvector; |
| |
| matrix_type M; |
| M = .... |
| |
| matrix_rowvector row2 = row(M, 2); |
| matrix_colvector col3 = col(M, 3); |
| ... |
| \endcode |
| |
| |
| |
| |
| |
| \section expr_print Expression printing |
| |
| Expression printing is a nice feature for debugging expressions. (For more |
| about expression templates and expression tree please have a look |
| <a href=http://extreme.indiana.edu/~tveldhui/papers/Expression-Templates/exprtmpl.html>here</a>). |
| |
| You can write out a simple matrix-vector multiplication of a vector |
| <tt>v1</tt> and a matrix <tt>m1</tt> of the dimension of 3 as follows: |
| |
| \par Example: |
| \code |
| std::cout << m1 * v1 << std::endl; |
| \endcode |
| |
| which will be expanded to: |
| |
| \par [continued] |
| \code |
| XprVector< |
| XprMVProduct< |
| d, 3, 3, 3, 1, d, 1 |
| > |
| 3 |
| > |
| \endcode |
| |
| The "d" is a g++ placeholder for double. (This may vary from compiler to |
| compiler since it is an implementation detail of runtime type information |
| [rtti] determined by the compiler's manufacturer). The purpose of this |
| feature is to check the right evaluation of expressions into the tree on |
| complicated mathematical expressions. |
| |
| A rich source of examples are the regression tests. They show all of the |
| supported operations and functions (if there is a regression test for this |
| of course). Some examples are in the examples directory. |
| |
| |
| |
| |
| */ |
| |
| |
| // Local Variables: |
| // mode:c++ |
| // End: |