source: trunk/yat/classifier/MatrixLookup.h @ 1565

Last change on this file since 1565 was 1565, checked in by Peter, 13 years ago

removed Policy from Container2DIterator - refs #398

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date ID
File size: 10.7 KB
Line 
1#ifndef _theplu_yat_classifier_matrix_lookup_
2#define _theplu_yat_classifier_matrix_lookup_
3
4// $Id$
5
6/*
7  Copyright (C) 2005 Peter Johansson, Markus Ringnér
8  Copyright (C) 2006 Jari Häkkinen, Peter Johansson, Markus Ringnér
9  Copyright (C) 2007 Jari Häkkinen, Peter Johansson
10  Copyright (C) 2008 Peter Johansson
11
12  This file is part of the yat library, http://dev.thep.lu.se/yat
13
14  The yat library is free software; you can redistribute it and/or
15  modify it under the terms of the GNU General Public License as
16  published by the Free Software Foundation; either version 3 of the
17  License, or (at your option) any later version.
18
19  The yat library is distributed in the hope that it will be useful,
20  but WITHOUT ANY WARRANTY; without even the implied warranty of
21  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22  General Public License for more details.
23
24  You should have received a copy of the GNU General Public License
25  along with yat. If not, see <http://www.gnu.org/licenses/>.
26*/
27
28#include "yat/utility/Container2DIterator.h"
29#include "yat/utility/Index.h"
30#include "yat/utility/iterator_traits.h"
31#include "yat/utility/Matrix.h"
32#include "yat/utility/SmartPtr.h"
33
34#include <boost/iterator/permutation_iterator.hpp>
35
36#include <iostream>
37#include <vector>
38
39namespace theplu {
40namespace yat {
41namespace classifier { 
42
43  ///
44  /// @brief General view into utility::Matrix
45  ///
46  /// MatrixLookups can be used to create lookups/views into matrices
47  /// in a more general way than the views supported in the matrix
48  /// class. The object does not contain any data, but only a pointer
49  /// to a utility::Matrix and row and columns incices defining which
50  /// sub-matrix to look into.  Each row and each column corresponds
51  /// to a row and a column in the utility::Matrix, respectively. This design
52  /// allow for fast creation of sub-matrices, which is a common
53  /// operation in most traning/validation procedures. The views are
54  /// const views in the sense that they cannot modify underlying
55  /// utility::Matrix.
56  ///
57  /// A MatrixLookup can be created directly from a utility::Matrix or from
58  /// another MatrixLookup. In the latter case, the resulting
59  /// MatrixLookup is looking directly into the underlying utility::Matrix to
60  /// avoid multiple lookups.
61  ///
62  /// There is a possibility to set the MatrixLookup as owner of the
63  /// underlying utility::Matrix. This implies that underlying data is deleted
64  /// in destructor of MatrixLookup, but only if there is no other
65  /// owner of the underlying data. A reference counter is used to
66  /// keep track of number of owners. Ownership is copied in copy
67  /// constructors and assignments.
68  ///
69  /// \see MatrixLookupWeighted
70  ///
71  class MatrixLookup
72  {
73  public:
74    /**
75       value_type is double
76
77       \since New in yat 0.5
78     */
79    typedef utility::Matrix::value_type value_type;
80
81    /**
82       const_reference type is const double&
83
84       \since New in yat 0.5
85     */
86    typedef utility::Matrix::const_reference const_reference;
87
88    /// 'Read Only' iterator
89    typedef utility::Container2DIterator<const MatrixLookup, value_type, 
90                                         const_reference>
91    const_iterator;
92
93    /**
94       'Read only' iterator used to iterate over a column
95     */
96    typedef boost::permutation_iterator<utility::Matrix::const_column_iterator,
97                                        utility::Index::const_iterator> 
98    const_column_iterator;
99
100    /**
101       'Read only' iterator used to iterate over a row
102     */
103    typedef const_column_iterator const_row_iterator;
104
105    ///
106    /// Constructor creating a lookup into the entire @a matrix.
107    /// \param matrix underlying matrix
108    /// @param own if true MatrixLookup owns its underlying @a matrix
109    ///
110    /// @note If \a own is true and \a matrix is already owned by some
111    /// other object, this will lead to \a matrix having multiple
112    /// owners without the owners being aware of each
113    /// other. Consequently multiple deletion will occur.
114    ///
115    /// @note If @a matrix goes out of scope or is deleted, the
116    /// MatrixLookup becomes invalid and the result of further use is
117    /// undefined.
118    ///
119    MatrixLookup(const utility::Matrix& matrix, const bool own=false);
120
121    ///
122    /// Constructor creating a lookup into a sub-matrix of @a matrix.
123    /// The @a row and @a column define what sub-matrix to look into,
124    /// in other words, the created MatrixLookup will fullfill the
125    /// following: \f$ MatrixLookup(i,j)=matrix(row[i],column[j])
126    /// \f$. This also means that number of rows in created
127    /// MatrixLookup is equal to size of vector @a row, and number of
128    /// columns is equal to size of vector @a column.
129    ///
130    /// @note If @a matrix goes out of scope or is deleted, the
131    /// MatrixLookup becomes invalid and the result of further use is
132    /// undefined.
133    ///
134    MatrixLookup(const utility::Matrix& matrix, const utility::Index& row, 
135                 const utility::Index& column);
136
137    ///
138    /// Constructor creating a lookup into a sub-matrix of @a matrix.
139    ///
140    /// If @a row_vectors is true the new MatrixLookup will consist
141    /// of the row vectors defined by @a index. This means that the
142    /// created MatrixLookup will fullfill:
143    /// \f$ MatrixLookup(i,j)=matrix(i,index[j]) \f$
144    ///
145    /// If @a row_vectors is false the new MatrixLookup will be consist
146    /// of the rolumn vectors defined by @a index. This means that the
147    /// created MatrixLookup will fullfill:
148    /// \f$ MatrixLookup(i,j)=matrix(index[i],j) \f$
149    ///
150    /// @note If @a matrix goes out of scope or is deleted, the
151    /// MatrixLookup becomes invalid and the result of further use is
152    /// undefined.
153    ///
154    MatrixLookup(const utility::Matrix& matrix, 
155                 const utility::Index& index, 
156                 const bool row_vectors);
157
158    ///
159    /// @brief Copy constructor.
160    ///
161    /// If \a other is owner of underlying data, constructed
162    /// MatrixLookup will also be set as owner of underlying data.
163    ///
164    /// @note If underlying matrix goes out of scope or is deleted, the
165    /// MatrixLookup becomes invalid and the result of further use is
166    /// undefined.
167    ///
168    MatrixLookup(const MatrixLookup& other);
169
170    ///
171    /// @brief Create a sub-MatrixLookup.
172    ///
173    /// The Lookup is independent of
174    /// MatrixLookup @a ml. The MatrixLookup is created to look
175    /// directly into the underlying matrix to avoid multiple lookups.
176    ///
177    /// If \a ml is owner of underlying data, constructed
178    /// MatrixLookup will also be set as owner of underlying data.
179    ///
180    /// The @a row and @a column define what sub-matrix to look into,
181    /// in other words, the created MatrixLookup will fullfill the
182    /// following: MatrixLookup(i,j)=ml(row[i],column[j]). This
183    /// also means that number of rows in created MatrixLookup is
184    /// equal to size of vector @a row, and number of columns is equal
185    /// to size of vector @a column.
186    ///
187    /// If \a ml is owner of underlying data, constructed
188    /// MatrixLookup will also be set as owner of underlying data.
189    ///
190    /// @note If underlying matrix goes out of scope or is deleted, the
191    /// MatrixLookup becomes invalid and the result of further use is
192    /// undefined.
193    ///
194    MatrixLookup(const MatrixLookup& ml, const utility::Index& row, 
195                 const utility::Index& column);
196
197    ///
198    /// Constructor creating a lookup into a sub-matrix of
199    /// @a ml. The MatrixLookup is created to look directly into the
200    /// underlying matrix to avoid multiple lookups.
201    ///
202    /// If @a row_vectors is true the new MatrixLookup will consist
203    /// of the row vectors defined by @a index. This means that the
204    /// created MatrixLookup will fullfill:
205    /// MatrixLookup(i,j)=ml(i,index[j])
206    ///
207    /// If @a row_vectors is false the new MatrixLookup will consist
208    /// of the rolumn vectors defined by @a index. This means that the
209    /// created MatrixLookup will fullfill:
210    /// \f$ MatrixLookup(i,j) = ml(index[i],j) \f$
211    ///
212    /// If \a ml is owner of underlying data, constructed
213    /// MatrixLookup will also be set as owner of underlying data.
214    ///
215    /// @note If underlying matrix goes out of scope or is deleted, the
216    /// MatrixLookup becomes invalid and the result of further use is
217    /// undefined.
218    ///
219    MatrixLookup(const MatrixLookup& ml, const utility::Index&, 
220                 const bool row_vectors);
221
222    ///
223    /// Constructor creating a MatrixLookup with @a rows rows, @a
224    /// columns columns, and all values are set to @a value. Created
225    /// MatrixLookup owns its underlying matrix.
226    ///
227    MatrixLookup(const size_t rows, const size_t columns, const double value=0);
228
229    ///
230    /// @brief The istream constructor.
231    ///
232    /// In construction the underlying matrix is created from
233    /// stream. The MatrixLookup will be owner of the underlying
234    /// matrix.
235    ///
236    /// @see matrix(istream&) for details.
237    ///
238    MatrixLookup(std::istream&, char sep='\0');
239
240    ///
241    /// @brief Destructor.
242    ///
243    /// If ownership is set true and there is no other owner of
244    /// underlying data, underlying data is deleted.
245    ///
246    virtual ~MatrixLookup();
247
248    /**
249       Iterator iterates along a row. When end of row is reached it
250       jumps to beginning of next row.
251
252       \return const_iterator pointing to upper-left element.
253     */
254    const_iterator begin(void) const;
255
256    /**
257       Iterator iterates along a column.
258
259       \return iterator pointing to first element of column \a i.
260     */
261    const_column_iterator begin_column(size_t) const;
262
263    /**
264       Iterator iterates along a column.
265
266       \return const_iterator pointing to first element of column \a i.
267     */
268    const_row_iterator begin_row(size_t) const;
269
270    /**
271       \return number of columns
272    */
273    size_t columns(void) const;
274
275    /**
276       \return const_iterator pointing to end of matrix
277     */
278    const_iterator end(void) const;
279
280    /**
281       \return const_iterator pointing to end of column \a i
282     */
283    const_column_iterator end_column(size_t) const;
284
285    /**
286       \return const_iterator pointing to end of row \a i
287     */
288    const_row_iterator end_row(size_t) const;
289
290    /**
291       \return number of rows
292    */
293    size_t rows(void) const;
294
295    ///
296    /// @return false
297    ///
298    bool weighted(void) const;
299
300    ///
301    /// Access operator
302    ///
303    /// @return element
304    ///
305    double operator()(const size_t row, const size_t column) const;
306
307    ///
308    /// @brief assigment operator
309    ///
310    /// Does only change MatrixLookup not the underlying matrix
311    /// object. However if the MatrixLookup is owner (and the only owner)
312    /// of its underlying
313    /// matrix, that matrix will be deleted here.
314    ///
315    const MatrixLookup& operator=(const MatrixLookup&);
316   
317  private:
318    friend class MatrixLookupWeighted;
319
320    utility::Index column_index_;
321    typedef utility::SmartPtr<const utility::Matrix> MatrixP;
322    MatrixP data_;
323    utility::Index row_index_;
324
325    // for assertions
326    bool validate(void) const;
327  }; 
328 
329  ///
330  /// The output operator MatrixLookup
331  ///
332  std::ostream& operator<< (std::ostream& s, const MatrixLookup&);
333
334}}} // of namespace classifier, yat, and theplu
335
336#endif
Note: See TracBrowser for help on using the repository browser.