source: trunk/yat/classifier/MatrixLookupWeighted.h @ 1091

Last change on this file since 1091 was 1091, checked in by Peter, 16 years ago

fixes #267 iterator for MatrixLookupWeighted?

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date ID
File size: 12.7 KB
Line 
1#ifndef _theplu_yat_classifier_matrix_lookup_weighted_
2#define _theplu_yat_classifier_matrix_lookup_weighted_
3
4// $Id$
5
6/*
7  Copyright (C) 2006 Jari Häkkinen, Markus Ringnér, Peter Johansson
8  Copyright (C) 2007 Jari Häkkinen, Peter Johansson
9
10  This file is part of the yat library, http://trac.thep.lu.se/yat
11
12  The yat library is free software; you can redistribute it and/or
13  modify it under the terms of the GNU General Public License as
14  published by the Free Software Foundation; either version 2 of the
15  License, or (at your option) any later version.
16
17  The yat library is distributed in the hope that it will be useful,
18  but WITHOUT ANY WARRANTY; without even the implied warranty of
19  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20  General Public License for more details.
21
22  You should have received a copy of the GNU General Public License
23  along with this program; if not, write to the Free Software
24  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
25  02111-1307, USA.
26*/
27
28#include "DataLookup2D.h"
29#include "yat/utility/Iterator.h"
30#include "yat/utility/IteratorPolicy.h"
31#include "yat/utility/StrideIterator.h"
32
33#include <iostream>
34#include <utility>
35#include <vector>
36
37namespace theplu {
38namespace yat {
39
40namespace utility {
41  class matrix;
42}
43
44namespace classifier { 
45
46  class MatrixLookup;
47
48  ///
49  /// @brief Class viewing into data and weight matrix.
50  ///
51  /// A MatrixLookupWeighted is very similar to a MatrixLookup, but
52  /// contains a pointer to a weight matrix as well meaning each data
53  /// element is associated to a weight.
54  ///
55  /// A MatrixLookupWeighted can be created directly from a matrix or
56  /// from an other MatrixLookupWeighted. In the latter case, the
57  /// resulting MatrixLookupWeighted is looking directly into the
58  /// underlying matrix to avoid multiple lookups.
59  ///
60  /// There is a possibility to set the MatrixLookupWeighted as owner
61  /// of the underlying matrices (data and weight).
62  /// This implies that underlying data is deleted
63  /// in destructor of MatrixLookupWeighted, but only if there is no other
64  /// owner of the underlying data. A reference counter is used to
65  /// keep track of number of owners. Ownership is copied in copy
66  /// constructors and assignments.
67  ///
68  class MatrixLookupWeighted : public DataLookup2D
69  {
70 
71  public:
72    /// 'Read Only' iterator
73    typedef utility::StrideIterator<
74    utility::Iterator<const MatrixLookupWeighted, 
75                      const std::pair<double, double>, void, 
76                      const std::pair<double, double>,
77                      utility::IteratorPolicyWeighted<const MatrixLookupWeighted,
78                                                      const double,
79                                                      const double> > >
80    const_iterator;
81
82    ///
83    /// Constructor creating a lookup into the entire \a matrix and \a
84    /// weights.
85    ///
86    /// @note If @a matrix or @a weights goes out of scope or is
87    /// deleted, the MatrixLookupWeighted becomes invalid and the
88    /// result of further use is undefined.
89    ///
90    MatrixLookupWeighted(const utility::matrix& matrix, 
91                         const utility::matrix& weights,
92                         const bool owner=false);
93
94   
95    ///
96    /// Constructor creating a lookup into the entire @a matrix.  A
97    /// weight matrix is constructed with weights 1 for values and 0
98    /// for nan's in @a matrix.
99    ///
100    /// \see  bool utility::nan(const matrix&, matrix&);
101    ///
102    /// @note If @a matrix goes out of scope or
103    /// is deleted, the MatrixLookupWeighted becomes invalid and the
104    /// result of further use is undefined.
105    ///
106    MatrixLookupWeighted(const utility::matrix& matrix);
107
108
109    /**
110       Constructor creating a MatrixLookupWeighted from a MatrixLookup. A
111       weight matrix with unitary weights are created internally.
112
113       \note no check for nan is performed.
114       
115       \see   bool utility::nan(const matrix&, matrix&);
116       
117       @note If @a matrix goes out of scope or
118       is deleted, the MatrixLookupWeighted becomes invalid and the
119       result of further use is undefined.
120    */
121    MatrixLookupWeighted(const MatrixLookup& matrix);
122
123
124    ///
125    /// Constructor creating a lookup into a sub-matrix of @a matrix.
126    /// The @a row and @a column define what sub-matrix to look into,
127    /// in other words, the created MatrixLookupWeighted will fullfill
128    /// the following:
129    /// MatrixLookupWeighted(i,j)=matrix(row[i],column[j])
130    /// weights(row[i],column[j]). This also means that number of
131    /// rows in created MatrixLookupWeighted is equal to size of
132    /// vector @a row, and number of columns is equal to size of
133    /// vector @a column.
134    ///
135    /// @note If @a matrix or @a weights goes out of scope or is deleted, the
136    /// MatrixLookupWeighted becomes invalid and the result of further use is
137    /// undefined.
138    ///
139    MatrixLookupWeighted(const utility::matrix& matrix, 
140                         const utility::matrix& weights, 
141                         const std::vector<size_t>& row, 
142                         const std::vector<size_t>& column);
143
144    ///
145    /// Constructor creating a lookup into a sub-matrix of @a matrix.
146    ///
147    /// If @a row_vectors is true the new MatrixLookupWeighted will be
148    /// consist of the row vectors defined by @a index. This means
149    /// that the created MatrixLookupWeighted will fullfill:
150    /// MatrixLookupWeighted(i,j)=matrix(i,index[j])*weights(i,index[j])
151    ///
152    ///
153    /// If @a row_vectors is false the new MatrixLookupWeighted will be consist
154    /// of the rolumn vectors defined by @a index. This means that the
155    /// created MatrixLookupWeighted will fullfill:
156    ///
157    ///
158    /// @note If @a matrix or @a weights goes out of scope or is
159    /// deleted, the MatrixLookupWeighted becomes invalid and the
160    /// result of further use is undefined.
161    ///
162    MatrixLookupWeighted(const utility::matrix& matrix, 
163                         const utility::matrix& weights, 
164                         const std::vector<size_t>& index, 
165                         const bool row_vectors);
166
167    ///
168    /// @brief Copy constructor.
169    ///
170    /// If \a other is owner of underlying data, constructed
171    /// MatrixLookup will also be set as owner of underlying data.
172    ///
173    /// @note If underlying matrix goes out of scope or is deleted, the
174    /// MatrixLookupWeighted becomes invalid and the result of further use is
175    /// undefined.
176    ///
177    MatrixLookupWeighted(const MatrixLookupWeighted& other);
178
179    ///
180    /// Creates a sub-MatrixLookupWeighted. The Lookup is independent of
181    /// MatrixLookupWeighted @a ml. The MatrixLookupWeighted is created to look
182    /// directly into the underlying matrix to avoid multiple lookups.
183    ///
184    /// The @a row and @a column define what sub-matrix to look into,
185    /// in other words, the created MatrixLookupWeighted will fullfill the
186    /// following: \f$ MatrixLookupWeighted(i,j)=ml(row[i],column[j]) \f$. This
187    /// also means that number of rows in created MatrixLookupWeighted is
188    /// equal to size of vector @a row, and number of columns is equal
189    /// to size of vector @a column.
190    ///
191    /// If \a ml is owner of underlying data, constructed
192    /// MatrixLookup will also be set as owner of underlying data.
193    ///
194    /// @note If underlying matrix goes out of scope or is deleted, the
195    /// MatrixLookupWeighted becomes invalid and the result of further use is
196    /// undefined.
197    ///
198    MatrixLookupWeighted(const MatrixLookupWeighted& ml, 
199                         const std::vector<size_t>& row, 
200                         const std::vector<size_t>& column);
201
202    ///
203    /// Constructor creating a lookup into a sub-matrix of
204    /// @a ml. The MatrixLookupWeighted is created to look directly into the
205    /// underlying matrix to avoid multiple lookups.
206    ///
207    /// If @a row_vectors is true the new MatrixLookupWeighted will consist
208    /// of the row vectors defined by @a index. This means that the
209    /// created MatrixLookupWeighted will fullfill:
210    /// \f$ MatrixLookupWeighted(i,j)=ml(i,index[j])\f$
211    ///
212    /// If @a row_vectors is false the new MatrixLookupWeighted will consist
213    /// of the rolumn vectors defined by @a index. This means that the
214    /// created MatrixLookupWeighted will fullfill:
215    /// \f$ MatrixLookupWeighted(i,j) = ml(index[i],j) \f$
216    ///
217    /// If \a ml is owner of underlying data, constructed
218    /// MatrixLookup will also be set as owner of underlying data.
219    ///
220    /// @note If underlying matrix goes out of scope or is deleted, the
221    /// MatrixLookupWeighted becomes invalid and the result of further use is
222    /// undefined.
223    ///
224    MatrixLookupWeighted(const MatrixLookupWeighted& ml, 
225                         const std::vector<size_t>&, 
226                         const bool row_vectors);
227
228    ///
229    /// Constructor creating a MatrixLookupWeighted with @a rows rows, @a
230    /// columns columns, and all values are set to @a value. Created
231    /// MatrixLookupWeighted owns its underlying matrix.
232    ///
233    MatrixLookupWeighted(const size_t rows, const size_t columns, 
234                         const double value=0, const double weight=1);
235
236    ///
237    /// @brief The istream constructor.
238    ///
239    /// In construction the underlying matrix is created from
240    /// stream. The MatrixLookupWeighted will be owner of the underlying
241    /// matrix.
242    ///
243    /// @see matrix(istream&) for details.
244    ///
245    MatrixLookupWeighted(std::istream&, char sep='\0');
246
247    ///
248    /// Destructor. If MatrixLookup is owner (and the only owner) of
249    /// underlying matrix, the matrices are destroyed.
250    ///
251    virtual ~MatrixLookupWeighted();
252
253    /**
254       Iterator iterates along a row. When end of row is reached it
255       jumps to beginning of next row.
256
257       \return const_iterator pointing to upper-left element.
258     */
259    const_iterator begin(void) const;
260
261    /**
262       Iterator iterates along a column.
263
264       \return iterator pointing to first element of column \a i.
265     */
266    const_iterator begin_column(size_t) const;
267
268    /**
269       Iterator iterates along a column.
270
271       \return const_iterator pointing to first element of column \a i.
272     */
273    const_iterator begin_row(size_t) const;
274
275    ///
276    /// @return data value of element (@a row, @a column)
277    ///
278    double data(size_t row, size_t column) const;
279
280    /**
281       \return const_iterator pointing to end of matrix
282     */
283    const_iterator end(void) const;
284
285    /**
286       \return const_iterator pointing to end of column \a i
287     */
288    const_iterator end_column(size_t) const;
289
290    /**
291       \return const_iterator pointing to end of row \a i
292     */
293    const_iterator end_row(size_t) const;
294
295    /**
296       the new MatrixLookup will consist of the rolumn vectors
297       defined by @a index. This means that the returned
298       MatrixLookupWeighted
299       will fullfill:
300       returned(i,j) = original(index[i],j)
301
302       @note If underlying matrix goes out of scope or is deleted, the
303       returned pointer becomes invalid and the result of further use is
304       undefined.
305   
306    */
307    const MatrixLookupWeighted* selected(const std::vector<size_t>& i) const;
308
309    ///
310    /// The created MatrixLookupWeighted corresponds to all rows and the
311    /// columns defined by @a index in the original MatrixLookupWeighted. The
312    /// created MatrixLookupWeighted will fullfill:
313    /// novel_ml(i,j)=original(i,index[j]).
314    ///
315    /// @return pointer to sub-Lookup of the MatrixLookupWeighted
316    ///
317    /// @note If underlying matrix goes out of scope or is deleted, the
318    /// returned pointer becomes invalid and the result of further use is
319    /// undefined.
320    ///
321    const MatrixLookupWeighted* 
322    training_data(const std::vector<size_t>& index) const;
323   
324    ///
325    /// The created MatrixLookupWeighted corresponds to all rows and the
326    /// columns defined by @a index in the original MatrixLookupWeighted. The
327    /// created MatrixLookupWeighted will fullfill:
328    /// novel_ml(i,j)=original(i,index[j])
329    ///
330    /// @return pointer to sub-Lookup of the MatrixLookupWeighted
331    ///
332    /// @note If underlying matrix goes out of scope or is deleted, the
333    /// returned pointer becomes invalid and the result of further use is
334    /// undefined.
335    ///
336    const MatrixLookupWeighted* validation_data(const std::vector<size_t>&,
337                                        const std::vector<size_t>&) const;
338
339    ///
340    /// @return weight value of element (@a row, @a column)
341    ///
342    double weight(size_t row, size_t column) const;
343
344    ///
345    /// @return true
346    ///
347    bool weighted(void) const;
348
349    ///
350    /// Access operator
351    ///
352    /// @return weight * data for element (@a row, @a column)
353    ///
354    double operator()(const size_t row, const size_t column) const;
355
356    ///
357    /// @brief assigment operator
358    ///
359    /// Does only change MatrixLookupWeighted not the underlying
360    /// matrix object. However if the MatrixLookupWeighted is owner
361    /// (and the only owner) of its underlying data, those data will
362    /// be deleted here.
363    ///
364    const MatrixLookupWeighted& operator=(const MatrixLookupWeighted&);
365   
366  private:
367    const utility::matrix* data_;
368    const utility::matrix* weights_;
369    u_int* ref_count_weights_;
370  }; 
371 
372  ///
373  /// The output operator MatrixLookupWeighted
374  ///
375  /// For eacd data element data(i,j) is printed except those being
376  /// associated with a zero weight for which nothing is printed.
377  ///
378  std::ostream& operator<< (std::ostream& s, const MatrixLookupWeighted&);
379
380}}} // of namespace classifier, yat, and theplu
381
382#endif
Note: See TracBrowser for help on using the repository browser.