[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]

accessor.hxx VIGRA

1 /************************************************************************/
2 /* */
3 /* Copyright 1998-2002 by Ullrich Koethe */
4 /* */
5 /* This file is part of the VIGRA computer vision library. */
6 /* The VIGRA Website is */
7 /* http://hci.iwr.uni-heidelberg.de/vigra/ */
8 /* Please direct questions, bug reports, and contributions to */
9 /* ullrich.koethe@iwr.uni-heidelberg.de or */
10 /* vigra@informatik.uni-hamburg.de */
11 /* */
12 /* Permission is hereby granted, free of charge, to any person */
13 /* obtaining a copy of this software and associated documentation */
14 /* files (the "Software"), to deal in the Software without */
15 /* restriction, including without limitation the rights to use, */
16 /* copy, modify, merge, publish, distribute, sublicense, and/or */
17 /* sell copies of the Software, and to permit persons to whom the */
18 /* Software is furnished to do so, subject to the following */
19 /* conditions: */
20 /* */
21 /* The above copyright notice and this permission notice shall be */
22 /* included in all copies or substantial portions of the */
23 /* Software. */
24 /* */
25 /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND */
26 /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES */
27 /* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND */
28 /* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT */
29 /* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, */
30 /* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING */
31 /* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR */
32 /* OTHER DEALINGS IN THE SOFTWARE. */
33 /* */
34 /************************************************************************/
35 
36 #ifndef VIGRA_ACCESSOR_HXX
37 #define VIGRA_ACCESSOR_HXX
38 
39 #include "metaprogramming.hxx"
40 #include "numerictraits.hxx"
41 #include "tuple.hxx"
42 
43 namespace vigra {
44 
45 /** \addtogroup DataAccessors Data Accessors
46 
47 Basic templates to encapsulate access to the data of an iterator.
48 
49 Data accessors are used to allow for flexible access to the data
50 an iterator points to. When we access the data directly, we
51 are bound to what <TT>operator*()</TT> returns, if this method exists at
52 all. Encapsulating access in an accessor enables a better
53 decoupling of data structures and algorithms.
54 <a href="http://ukoethe.github.io/vigra/doc/vigra/documents/DataAccessors.ps">This paper</a> contains
55 a detailed description of the concept. Here is a brief list of the basic
56 accessor requirements:
57 
58 <p>
59 <table border=2 cellspacing=0 cellpadding=2 width="100%">
60 <tr><th>
61  Operation
62  </th><th>
63  Result
64  </th><th>
65  Semantics
66  </th>
67 </tr>
68 <tr>
69  <td><tt>accessor(iter)</tt></td><td>convertible to <br><tt>Accessor::value_type const &</tt></td>
70  <td>read data at the current position of the iterator</td>
71 </tr>
72 <tr>
73  <td><tt>accessor(iter, index)</tt></td><td>convertible to <br><tt>Accessor::value_type const &</tt></td>
74  <td>read data at offset <tt>index</tt> relative to iterator's current position
75  (random-access iterator only)</td>
76 </tr>
77 <tr>
78  <td><tt>accessor.set(value, iter)</tt></td><td><tt>void</tt></td>
79  <td>write data <tt>value</tt> at the current position of the iterator (mutable iterator only)</td>
80 </tr>
81 <tr>
82  <td><tt>accessor.set(value, iter, index)</tt></td><td><tt>void</tt></td>
83  <td>write data <tt>value</tt> at offset <tt>index</tt> relative to iterator's current position
84  (mutable random-access iterator only)</td>
85 </tr>
86 <tr><td colspan=2>
87  <tt>Accessor::value_type</tt></td>
88  <td>type of the data field the accessor refers to</td>
89 </tr>
90 <tr><td colspan=3>
91  <tt>iter</tt> is an iterator<br>
92  <tt>index</tt> has the iterator's index type (<tt>Iterator::difference_type</tt>)<br>
93  <tt>value</tt> is convertible to <tt>Accessor::value_type const &</tt>
94  </td>
95 </tr>
96 </table>
97 </p>
98 
99 The template <tt>AccessorTraits<T></tt> can be used to find the default accessor
100 associated with the type <tt>T</tt>, e.g.
101 
102 \code
103 typedef typename AccessorTraits<typename Image::value_type>::default_accessor Accessor;
104 typedef typename AccessorTraits<typename Image::value_type>::default_const_accessor ConstAccessor;
105 \endcode
106 */
107 //@{
108 
109 /********************************************************/
110 /* */
111 /* StandardAccessor */
112 /* */
113 /********************************************************/
114 
115 /** \brief Encapsulate access to the values an iterator points to.
116 
117  StandardAccessor is a trivial accessor that simply encapsulates
118  the iterator's operator*() and operator[]() in its
119  read and write functions. It passes its arguments <em>by reference</em>.
120  If you want to return items by value, you
121  must use StandardValueAccessor instead of StandardAccessor.
122  Both accessors have different optimization properties --
123  StandardAccessor is usually faster for compound pixel types,
124  while StandardValueAccessor is faster for the built-in types.
125 
126  When a floating point number is assigned by means of an accessor
127  with integral value_type, the value is rounded and clipped as appropriate.
128 
129  <b>\#include</b> <vigra/accessor.hxx><br>
130  Namespace: vigra
131 */
132 template <class VALUETYPE>
134 {
135  public:
136  /** the value_type
137  */
138  typedef VALUETYPE value_type;
139 
140  /** read the current data item
141  */
142  template <class ITERATOR>
143  VALUETYPE const & operator()(ITERATOR const & i) const { return *i; }
144 
145  VALUETYPE const & operator()(VALUETYPE const * i) const { return *i; }
146 
147  /** read the data item at an offset (can be 1D or 2D or higher order difference).
148  */
149  template <class ITERATOR, class OFFSET>
150  VALUETYPE const & operator()(ITERATOR const & i, OFFSET const & diff) const
151  {
152  return i[diff];
153  }
154 
155  /** Write the current data item. The type <TT>V</TT> of the passed
156  in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
157  In case of a conversion floating point -> integral this includes rounding and clipping.
158  */
159  template <class V, class ITERATOR>
160  void set(V const & value, ITERATOR const & i) const
161  { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
162 
163  /* This overload is needed to make the accessor work with a std::back_inserter */
164  template <class V, class ITERATOR>
165  void set(V const & value, ITERATOR & i) const
166  { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
167 
168  /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
169  The type <TT>V</TT> of the passed
170  in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
171  In case of a conversion floating point -> integral this includes rounding and clipping.
172  */
173  template <class V, class ITERATOR, class OFFSET>
174  void set(V const & value, ITERATOR const & i, OFFSET const & diff) const
175  {
176  i[diff]= detail::RequiresExplicitCast<VALUETYPE>::cast(value);
177  }
178 };
179 
180 /** \brief Encapsulate access to the values an iterator points to.
181 
182  StandardValueAccessor is a trivial accessor that simply encapsulates
183  the iterator's operator*() and operator[]() in its
184  read and write functions. It passes its arguments <em>by value</em>.
185  If the iterator returns its items by reference (such as \ref vigra::ImageIterator),
186  you can also use StandardAccessor.
187  These accessors have different optimization properties --
188  StandardAccessor is usually faster for compound pixel types,
189  while StandardValueAccessor is faster for the built-in types.
190 
191  When a floating point number is assigned by means of an accessor
192  with integral value_type, the value is rounded and clipped as appropriate.
193 
194  <b>\#include</b> <vigra/accessor.hxx><br>
195  Namespace: vigra
196 */
197 template <class VALUETYPE>
199 {
200  public:
201  /** the value_type
202  */
203  typedef VALUETYPE value_type;
204 
205  /** Read the current data item. The type <TT>ITERATOR::reference</TT>
206  is automatically converted to <TT>VALUETYPE</TT>.
207  In case of a conversion floating point -> integral this includes rounding and clipping.
208  */
209  template <class ITERATOR>
210  VALUETYPE operator()(ITERATOR const & i) const
211  { return detail::RequiresExplicitCast<VALUETYPE>::cast(*i); }
212 
213  /** Read the data item at an offset (can be 1D or 2D or higher order difference).
214  The type <TT>ITERATOR::index_reference</TT>
215  is automatically converted to <TT>VALUETYPE</TT>.
216  In case of a conversion floating point -> integral this includes rounding and clipping.
217  */
218  template <class ITERATOR, class OFFSET>
219  VALUETYPE operator()(ITERATOR const & i, OFFSET const & diff) const
220  {
221  return detail::RequiresExplicitCast<VALUETYPE>::cast(i[diff]);
222  }
223  /** Write the current data item. The type <TT>V</TT> of the passed
224  in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
225  In case of a conversion floating point -> integral this includes rounding and clipping.
226  */
227  template <class V, class ITERATOR>
228  void set(V value, ITERATOR const & i) const
229  { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
230 
231  /* This overload is needed to make the accessor work with a std::back_inserter */
232  template <class V, class ITERATOR>
233  void set(V value, ITERATOR & i) const
234  { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
235 
236  /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
237  The type <TT>V</TT> of the passed
238  in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
239  In case of a conversion floating point -> integral this includes rounding and clipping.
240  */
241  template <class V, class ITERATOR, class OFFSET>
242  void set(V value, ITERATOR const & i, OFFSET const & diff) const
243  {
244  i[diff]= detail::RequiresExplicitCast<VALUETYPE>::cast(value);
245  }
246 };
247 
248 /********************************************************/
249 /* */
250 /* StandardConstAccessor */
251 /* */
252 /********************************************************/
253 
254 /** \brief Encapsulate read access to the values an iterator points to.
255 
256  StandardConstAccessor is a trivial accessor that simply encapsulates
257  the iterator's operator*() and operator[]() in its
258  read functions. It passes its arguments <em>by reference</em>.
259  If the iterator returns its items by value (such as \ref vigra::CoordinateIterator), you
260  must use StandardConstValueAccessor instead of StandardConstAccessor.
261  Both accessors also have different optimization properties --
262  StandardConstAccessor is usually faster for compound pixel types,
263  while StandardConstValueAccessor is faster for the built-in types.
264 
265  <b>\#include</b> <vigra/accessor.hxx><br>
266  Namespace: vigra
267 */
268 template <class VALUETYPE>
270 {
271  public:
272  typedef VALUETYPE value_type;
273 
274  /** read the current data item
275  */
276  template <class ITERATOR>
277  VALUETYPE const & operator()(ITERATOR const & i) const
278  { return *i; }
279 
280  /** read the data item at an offset (can be 1D or 2D or higher order difference).
281  */
282  template <class ITERATOR, class OFFSET>
283  VALUETYPE const & operator()(ITERATOR const & i, OFFSET const & diff) const
284  {
285  return i[diff];
286  }
287 };
288 
289 /** \brief Encapsulate access to the values an iterator points to.
290 
291  StandardConstValueAccessor is a trivial accessor that simply encapsulates
292  the iterator's operator*() and operator[]() in its
293  read functions. It passes its arguments <em>by value</em>.
294  If the iterator returns its items by reference (such as \ref vigra::ConstImageIterator),
295  you can also use StandardConstAccessor.
296  These accessors have different optimization properties --
297  StandardConstAccessor is usually faster for compound pixel types,
298  while StandardConstValueAccessor is faster for the built-in types.
299 
300  When an iterator passes a floating point number to an accessor
301  with integral value_type, the value is rounded and clipped as appropriate.
302 
303  <b>\#include</b> <vigra/accessor.hxx><br>
304  Namespace: vigra
305 */
306 template <class VALUETYPE>
308 {
309  public:
310  typedef VALUETYPE value_type;
311 
312  /** Read the current data item. The type <TT>ITERATOR::reference</TT>
313  is automatically converted to <TT>VALUETYPE</TT>.
314  In case of a conversion floating point -> integral this includes rounding and clipping.
315  */
316  template <class ITERATOR>
317  VALUETYPE operator()(ITERATOR const & i) const
318  { return detail::RequiresExplicitCast<VALUETYPE>::cast(*i); }
319 
320  /** Read the data item at an offset (can be 1D or 2D or higher order difference).
321  The type <TT>ITERATOR::index_reference</TT>
322  is automatically converted to <TT>VALUETYPE</TT>.
323  In case of a conversion floating point -> integral this includes rounding and clipping.
324  */
325  template <class ITERATOR, class OFFSET>
326  VALUETYPE operator()(ITERATOR const & i, OFFSET const & diff) const
327  {
328  return detail::RequiresExplicitCast<VALUETYPE>::cast(i[diff]);
329  }
330 };
331 
332 /********************************************************/
333 /* */
334 /* VectorComponentAccessor */
335 /* */
336 /********************************************************/
337 
338 /** \brief Accessor for one component of a vector.
339 
340  This accessor allows to select a single component (a single 'band')
341  of a vector valued pixel type. The pixel type must support
342  <TT>operator[]</TT>. The index of the component to be selected
343  is passed in the constructor. The accessor returns its items
344  <em>by reference</em>. If you want to pass/return items by value,
345  use VectorComponentValueAccessor. If a floating point number
346  is assigned by means of an accessor with integral value_type, the
347  value is rounded and clipped as appropriate.
348 
349  <b>Usage:</b>
350 
351  \code
352  vigra::BRGBImage image(w,h);
353 
354  // init red channel with 255
355  initImage(destImageRange(image,
356  VectorComponentAccessor<vigra::BRGBImage::value_type>(0)),
357  255);
358  \endcode
359 
360  <b>\#include</b> <vigra/accessor.hxx><br>
361  Namespace: vigra
362 
363 */
364 template <class VECTORTYPE>
366 {
367  int index_;
368  public:
369  /** the value_type
370  */
371  typedef typename VECTORTYPE::value_type value_type;
372 
373  /** determine the component to be accessed
374  */
376  : index_(index)
377  {}
378 
379  /** read the current data item
380  */
381  template <class ITERATOR>
382  value_type const & operator()(ITERATOR const & i) const
383  { return (*i)[index_]; }
384 
385  /** read the data item at an offset (can be 1D or 2D or higher order difference).
386  */
387  template <class ITERATOR, class OFFSET>
388  value_type const & operator()(ITERATOR const & i, OFFSET const & diff) const
389  {
390  return i[diff][index_];
391  }
392 
393  /** Write the current data item. The type <TT>V</TT> of the passed
394  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
395  In case of a conversion floating point -> integral this includes rounding and clipping.
396  */
397  template <class V, class ITERATOR>
398  void set(V const & value, ITERATOR const & i) const
399  {
400  (*i)[index_] = detail::RequiresExplicitCast<value_type>::cast(value);
401  }
402 
403  /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
404  The type <TT>V</TT> of the passed
405  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
406  In case of a conversion floating point -> integral this includes rounding and clipping.
407  */
408  template <class V, class ITERATOR, class OFFSET>
409  void set(V const & value, ITERATOR const & i, OFFSET const & diff) const
410  {
411  i[diff][index_]= detail::RequiresExplicitCast<value_type>::cast(value);
412  }
413 
414  /** Reset the index to the given number.
415  */
416  void setIndex(int i)
417  {
418  index_ = i;
419  }
420 };
421 
422 /** \brief Accessor for one component of a vector.
423 
424  This accessor allows to select a single component (a single 'band')
425  of a vector valued pixel type. The pixel type must support
426  <TT>operator[]</TT>. The index of the component to be selected
427  is passed in the constructor. The accessor returns its items
428  <em>by value</em>. If you want to pass/return items by reference,
429  use VectorComponentAccessor. If a floating point number
430  is assigned by means of an accessor with integral value_type, the
431  value is rounded and clipped as appropriate.
432 
433  <b>Usage:</b>
434 
435  \code
436  vigra::BRGBImage image(w,h);
437 
438  // init red channel with 255
439  initImage(destImageRange(image,
440  VectorComponentValueAccessor<vigra::BRGBImage::value_type>(0)),
441  255);
442  \endcode
443 
444  <b>\#include</b> <vigra/accessor.hxx><br>
445  Namespace: vigra
446 
447 */
448 template <class VECTORTYPE>
450 {
451  int index_;
452  public:
453  /** the value_type
454  */
455  typedef typename VECTORTYPE::value_type value_type;
456 
457  /** determine the component to be accessed
458  */
460  : index_(index)
461  {}
462 
463  /** Read the current data item.
464  The type <TT>ITERATOR::index_reference::value_type</TT>
465  is automatically converted to <TT>value_type</TT>.
466  In case of a conversion floating point -> integral this includes rounding and clipping.
467  */
468  template <class ITERATOR>
469  value_type operator()(ITERATOR const & i) const
470  { return detail::RequiresExplicitCast<value_type>::cast((*i)[index_]); }
471 
472  /** Read the data item at an offset (can be 1D or 2D or higher order difference).
473  The type <TT>ITERATOR::index_reference::value_type</TT>
474  is automatically converted to <TT>value_type</TT>.
475  In case of a conversion floating point -> integral this includes rounding and clipping.
476  */
477  template <class ITERATOR, class OFFSET>
478  value_type operator()(ITERATOR const & i, OFFSET const & diff) const
479  {
480  return detail::RequiresExplicitCast<value_type>::cast(i[diff][index_]);
481  }
482 
483  /** Write the current data item. The type <TT>V</TT> of the passed
484  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
485  In case of a conversion floating point -> integral this includes rounding and clipping.
486  */
487  template <class V, class ITERATOR>
488  void set(V value, ITERATOR const & i) const
489  {
490  (*i)[index_] = detail::RequiresExplicitCast<value_type>::cast(value);
491  }
492 
493  /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
494  The type <TT>V</TT> of the passed
495  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
496  In case of a conversion floating point -> integral this includes rounding and clipping.
497  */
498  template <class V, class ITERATOR, class OFFSET>
499  void set(V value, ITERATOR const & i, OFFSET const & diff) const
500  {
501  i[diff][index_]= detail::RequiresExplicitCast<value_type>::cast(value);
502  }
503 
504  /** Reset the index to the given number.
505  */
506  void setIndex(int i)
507  {
508  index_ = i;
509  }
510 };
511 
512 /********************************************************/
513 /* */
514 /* VectorElementAccessor */
515 /* */
516 /********************************************************/
517 
518 /** \brief Accessor for one component of a vector.
519 
520  This works like VectorComponentAccessor, only the template parameters differ:
521  Here, we need a vector accessor type , whereas VectorComponentAccessor requires a vector type.
522 
523  <b>Usage:</b>
524 
525  \code
526  vigra::BRGBImage image(w,h);
527 
528  // init red channel with 255
529  initImage(destImageRange(image,
530  VectorElementAccessor<vigra::BRGBImage::Accessor>(0)),
531  255);
532  \endcode
533 
534  <b>\#include</b> <vigra/accessor.hxx><br>
535  Namespace: vigra
536 
537 */
538 template <class ACCESSOR>
540 {
541  int index_;
542  ACCESSOR a_;
543  public:
544  /** the value_type
545  */
546  typedef typename ACCESSOR::component_type value_type;
547 
548  /** determine the component to be accessed
549  */
550  VectorElementAccessor(int index, ACCESSOR a = ACCESSOR())
551  : index_(index),
552  a_(a)
553  {}
554 
555  /** read the current data item
556  */
557  template <class ITERATOR>
558  value_type const & operator()(ITERATOR const & i) const
559  { return a_.getComponent(i, index_); }
560 
561  /** read the data item at an offset (can be 1D or 2D or higher order difference).
562  */
563  template <class ITERATOR, class OFFSET>
564  value_type const & operator()(ITERATOR const & i, OFFSET const & diff) const
565  {
566  return a_.getComponent(i, diff, index_);
567  }
568 
569  /** Write the current data item. The type <TT>V</TT> of the passed
570  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
571  In case of a conversion floating point -> integral this includes rounding and clipping.
572  */
573  template <class V, class ITERATOR>
574  void set(V const & value, ITERATOR const & i) const
575  {
576  a_.setComponent(detail::RequiresExplicitCast<value_type>::cast(value), i, index_);
577  }
578 
579  /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
580  The type <TT>V</TT> of the passed
581  in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
582  In case of a conversion floating point -> integral this includes rounding and clipping.
583  */
584  template <class V, class ITERATOR, class OFFSET>
585  void set(V const & value, ITERATOR const & i, OFFSET const & diff) const
586  {
587  a_.setComponent(detail::RequiresExplicitCast<value_type>::cast(value), i, diff, index_);
588  }
589 
590  /** Reset the index to the given number.
591  */
592  void setIndex(int i)
593  {
594  index_ = i;
595  }
596 };
597 
598 /********************************************************/
599 /* */
600 /* SequenceAccessor */
601 /* */
602 /********************************************************/
603 
604 /** \brief Accessor for items that are STL compatible sequences.
605 
606  It encapsulates access to the sequences' begin() and end()
607  functions.
608 
609  <b>Usage:</b>
610 
611  <b>\#include</b> <vigra/accessor.hxx><br>
612  Namespace: vigra
613 
614  \code
615  typedef std::list<std::list<int> > ListOfLists;
616 
617  ListOfLists ll;
618  ...
619 
620  typedef vigra::SequenceAccessor<ListOfLists::value_type> ListOfListsAccessor;
621  ListOfListsAccessor a;
622  for(ListOfLists::iterator li = ll.begin(); li != ll.end(); ++li)
623  {
624  for(ListOfListsAccessor::iterator i = a.begin(li); i != a.end(li); ++i)
625  {
626  *i = 10;
627  }
628  }
629  \endcode
630 */
631 template <class SEQUENCE>
633 : public StandardAccessor<SEQUENCE>
634 {
635  public:
636  /** the sequence's value_type
637  */
638  typedef typename SEQUENCE::value_type component_type;
639 
640 #ifndef NO_PARTIAL_TEMPLATE_SPECIALIZATION
641  typedef typename
642  If<typename TypeTraits<SEQUENCE>::isConst,
643  typename SEQUENCE::const_iterator,
644  typename SEQUENCE::iterator>::type
645  iterator;
646 #else
647  /** the sequence's iterator type
648  */
649  typedef typename SEQUENCE::iterator iterator;
650 #endif
651 
652  /** get begin iterator for sequence at given iterator position
653  */
654  template <class ITERATOR>
655  iterator begin(ITERATOR const & i) const
656  {
657  return (*i).begin();
658  }
659 
660  /** get end iterator for sequence at given iterator position
661  */
662  template <class ITERATOR>
663  iterator end(ITERATOR const & i) const
664  {
665  return (*i).end();
666  }
667 
668  /** get begin iterator for sequence at an offset
669  of given iterator position
670  */
671  template <class ITERATOR, class OFFSET>
672  iterator begin(ITERATOR const & i, OFFSET const & diff) const
673  {
674  return i[diff].begin();
675  }
676 
677  /** get end iterator for sequence at a 2D difference vector
678  of given iterator position
679  */
680  template <class ITERATOR, class OFFSET>
681  iterator end(ITERATOR const & i, OFFSET const & diff) const
682  {
683  return i[diff].end();
684  }
685 
686  /** get size of sequence at given iterator position
687  */
688  template <class ITERATOR>
689  unsigned int size(ITERATOR const & i) const { return (*i).size(); }
690 
691  /** get size of sequence at 2D difference vector of given iterator position
692  */
693  template <class ITERATOR, class OFFSET>
694  unsigned int size(ITERATOR const & i, OFFSET const & diff) const
695  { return i[diff].size(); }
696 };
697 
698 /********************************************************/
699 /* */
700 /* VectorAccessor */
701 /* */
702 /********************************************************/
703 
704 /** \brief Accessor for items that are STL compatible vectors.
705 
706  It encapsulates access to a vector's access functionality.
707 
708  <b> Usage:</b>
709 
710  <b>\#include</b> <vigra/accessor.hxx><br>
711  Namespace: vigra
712 
713  The accessor has two modes of operation:
714 
715  <ol>
716  <li> Access the vector's iterator via the <TT>begin()</TT> and <TT>end()</TT>
717  functions:
718 
719  \code
720  typedef std::list<std::vector<int> > ListOfVectors;
721 
722  ListOfVectors ll;
723  ...
724 
725  typedef vigra::SequenceAccessor<ListOfVectors::value_type> ListOfVectorsAccessor;
726  ListOfVectorsAccessor a;
727  for(ListOfVectors::iterator li = ll.begin(); li != ll.end(); ++li)
728  {
729  for(ListOfVectorsAccessor::iterator i = a.begin(li); i != a.end(li); ++i)
730  {
731  *i = 10;
732  }
733  }
734  \endcode
735  <li> Access the vector's components via an index (internally calls
736  the vector's <TT>operator[]</TT> ):
737  \code
738  typedef std::list<std::vector<int> > ListOfVectors;
739 
740  ListOfVectors ll;
741  ...
742 
743  typedef vigra::SequenceAccessor<ListOfVectors::value_type> ListOfVectorsAccessor;
744  ListOfVectorsAccessor a;
745  for(ListOfVectors::iterator li = ll.begin(); li != ll.end(); ++li)
746  {
747  for(int i = 0; i != a.size(li); ++i)
748  {
749  a.setComponent(10, li, i);
750  }
751  }
752  \endcode
753  </ol>
754 
755  <b> Required Interface:</b>
756 
757  \code
758  VECTOR v;
759  VECTOR::iterator i;
760  value_type d;
761  int index;
762 
763  d = v[index];
764  v[index] = d;
765  i = v.begin();
766  i = v.end();
767  v.size();
768  \endcode
769 */
770 template <class VECTOR>
772 : public SequenceAccessor<VECTOR>
773 {
774  public:
775  /** the vector's value_type
776  */
777  typedef typename VECTOR::value_type component_type;
778 
779  /** the vector element accessor associated with this vector accessor
780  (see \ref VectorElementAccessor)
781  */
783 
784  /** Read the component data at given vector index
785  at given iterator position
786  */
787  template <class ITERATOR>
788  component_type const & getComponent(ITERATOR const & i, int idx) const
789  {
790  return (*i)[idx];
791  }
792 
793  /** Set the component data at given vector index
794  at given iterator position. The type <TT>V</TT> of the passed
795  in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
796  In case of a conversion floating point -> integral this includes rounding and clipping.
797  */
798  template <class V, class ITERATOR>
799  void setComponent(V const & value, ITERATOR const & i, int idx) const
800  {
801  (*i)[idx] = detail::RequiresExplicitCast<component_type>::cast(value);
802  }
803 
804  /** Read the component data at given vector index
805  at an offset of given iterator position
806  */
807  template <class ITERATOR, class OFFSET>
808  component_type const & getComponent(ITERATOR const & i, OFFSET const & diff, int idx) const
809  {
810  return i[diff][idx];
811  }
812 
813  /** Set the component data at given vector index
814  at an offset of given iterator position. The type <TT>V</TT> of the passed
815  in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
816  In case of a conversion floating point -> integral this includes rounding and clipping.
817  */
818  template <class V, class ITERATOR, class OFFSET>
819  void
820  setComponent(V const & value, ITERATOR const & i, OFFSET const & diff, int idx) const
821  {
822  i[diff][idx] = detail::RequiresExplicitCast<component_type>::cast(value);
823  }
824 };
825 
826 
827 /********************************************************/
828 /* */
829 /* MultiImageAccessor2 */
830 /* */
831 /********************************************************/
832 
833 /** \brief Access two images simultaneously.
834 
835  This accessor is used when two images need to be treated as one
836  because an algorithm accepts only one image. For example,
837  \ref seededRegionGrowing() uses only one image two calculate
838  the cost for aggregating each pixel into a region. Sometimes, we
839  need more information to calculate this cost, for example gray value
840  and local gradient magnitude. These values can be stored in two images,
841  which appear as only one when we pass a <TT>MultiImageAccessor2</TT> to
842  the algorithms. Of course, the cost functor must accept a <TT>pair</TT>
843  of values for this to work. Instead of an actual image iterator, we
844  pass a <a href="CoordinateIterator.html">CoordinateIterator</a> which
845  selects the right pixels form both images.
846 
847  <b> Usage:</b>
848 
849  <b>\#include</b> <vigra/accessor.hxx><br>
850  Namespace: vigra
851 
852  \code
853  using namespace vigra;
854 
855  FImage gray_values(w,h), gradient_magnitude(w,h);
856  IImage seeds(w,h), labels(w,h);
857 
858  seededRegionGrowing(
859  srcIterRange(CoordinateIterator(), CoordinateIterator(w,h),
860  MultiImageAccessor2<FImage::iterator, FImage::Accessor,
861  FImage::iterator, FImage::Accessor>
862  (gray_values.upperLeft(), gray_values.accessor(),
863  gradient_magnitude.upperLeft(), gradient_magnitude.accessor())),
864  srcImage(seeds),
865  destImage(labels),
866  SomeCostFunctor());
867  \endcode
868 */
869 
870 template <class Iter1, class Acc1, class Iter2, class Acc2>
872 {
873  public:
874  /** The accessors value_type: construct a pair that contains
875  the corresponding image values.
876  */
877  typedef pair<typename Acc1::value_type, typename Acc2::value_type>
879 
880  /** Construct from two image iterators and associated accessors.
881  */
882  MultiImageAccessor2(Iter1 i1, Acc1 a1, Iter2 i2, Acc2 a2)
883  : i1_(i1), a1_(a1), i2_(i2), a2_(a2)
884  {}
885 
886  /** read the current data item
887  */
888  template <class OFFSET>
889  value_type operator()(OFFSET const & d) const
890  {
891  return std::make_pair(a1_(i1_, d), a2_(i2_, d));
892  }
893 
894  /** read the data item at an offset
895  */
896  template <class OFFSET1, class OFFSET2>
897  value_type operator()(OFFSET1 d1, OFFSET2 const & d2) const
898  {
899  d1 += d2;
900  return std::make_pair(a1_(i1_, d1), a2_(i2_, d1));
901  }
902 
903  private:
904  Iter1 i1_;
905  Acc1 a1_;
906  Iter2 i2_;
907  Acc2 a2_;
908 };
909 
910 //@}
911 
912 template <class T>
913 struct AccessorTraits
914 {
915  typedef StandardAccessor<T> default_accessor;
916  typedef StandardConstAccessor<T> default_const_accessor;
917 };
918 
919 #define VIGRA_DEFINE_ACCESSOR_TRAITS(VALUE, ACCESSOR, CONST_ACCESSOR) \
920  template <> \
921  struct AccessorTraits<VALUE > \
922  { \
923  typedef ACCESSOR<VALUE > default_accessor; \
924  typedef CONST_ACCESSOR<VALUE > default_const_accessor; \
925  };
926 
927 VIGRA_DEFINE_ACCESSOR_TRAITS(signed char, StandardValueAccessor, StandardConstValueAccessor)
928 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned char, StandardValueAccessor, StandardConstValueAccessor)
929 VIGRA_DEFINE_ACCESSOR_TRAITS(short, StandardValueAccessor, StandardConstValueAccessor)
930 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned short, StandardValueAccessor, StandardConstValueAccessor)
931 VIGRA_DEFINE_ACCESSOR_TRAITS(int, StandardValueAccessor, StandardConstValueAccessor)
932 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned int, StandardValueAccessor, StandardConstValueAccessor)
933 VIGRA_DEFINE_ACCESSOR_TRAITS(long, StandardValueAccessor, StandardConstValueAccessor)
934 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned long, StandardValueAccessor, StandardConstValueAccessor)
935 VIGRA_DEFINE_ACCESSOR_TRAITS(float, StandardValueAccessor, StandardConstValueAccessor)
936 VIGRA_DEFINE_ACCESSOR_TRAITS(double, StandardValueAccessor, StandardConstValueAccessor)
937 
938 template <class T, unsigned int RED_IDX, unsigned int GREEN_IDX, unsigned int BLUE_IDX> class RGBValue;
939 template <class T> class RGBAccessor;
940 template <class T, int SIZE> class TinyVector;
941 
942 #ifndef NO_PARTIAL_TEMPLATE_SPECIALIZATION
943 
944 template <class T, unsigned int RED_IDX, unsigned int GREEN_IDX, unsigned int BLUE_IDX>
945 struct AccessorTraits<RGBValue<T, RED_IDX, GREEN_IDX, BLUE_IDX> >
946 {
948  typedef RGBAccessor<RGBValue<T, RED_IDX, GREEN_IDX, BLUE_IDX> > default_const_accessor;
949 };
950 
951 template <class T, int SIZE>
952 struct AccessorTraits<TinyVector<T, SIZE> >
953 {
954  typedef VectorAccessor<TinyVector<T, SIZE> > default_accessor;
955  typedef VectorAccessor<TinyVector<T, SIZE> > default_const_accessor;
956 };
957 
958 #else // NO_PARTIAL_TEMPLATE_SPECIALIZATION
959 
960 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned char>, RGBAccessor, RGBAccessor)
961 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<signed char>, RGBAccessor, RGBAccessor)
962 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<short>, RGBAccessor, RGBAccessor)
963 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned short>, RGBAccessor, RGBAccessor)
964 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<int>, RGBAccessor, RGBAccessor)
965 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned int>, RGBAccessor, RGBAccessor)
966 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<long>, RGBAccessor, RGBAccessor)
967 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned long>, RGBAccessor, RGBAccessor)
968 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<float>, RGBAccessor, RGBAccessor)
969 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<double>, RGBAccessor, RGBAccessor)
970 
971 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 2>
972 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
973 #undef VIGRA_PIXELTYPE
974 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 3>
975 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
976 #undef VIGRA_PIXELTYPE
977 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 4>
978 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
979 #undef VIGRA_PIXELTYPE
980 #define VIGRA_PIXELTYPE TinyVector<short, 2>
981 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
982 #undef VIGRA_PIXELTYPE
983 #define VIGRA_PIXELTYPE TinyVector<short, 3>
984 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
985 #undef VIGRA_PIXELTYPE
986 #define VIGRA_PIXELTYPE TinyVector<short, 4>
987 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
988 #undef VIGRA_PIXELTYPE
989 #define VIGRA_PIXELTYPE TinyVector<int, 2>
990 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
991 #undef VIGRA_PIXELTYPE
992 #define VIGRA_PIXELTYPE TinyVector<int, 3>
993 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
994 #undef VIGRA_PIXELTYPE
995 #define VIGRA_PIXELTYPE TinyVector<int, 4>
996 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
997 #undef VIGRA_PIXELTYPE
998 #define VIGRA_PIXELTYPE TinyVector<float, 2>
999 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1000 #undef VIGRA_PIXELTYPE
1001 #define VIGRA_PIXELTYPE TinyVector<float, 3>
1002 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1003 #undef VIGRA_PIXELTYPE
1004 #define VIGRA_PIXELTYPE TinyVector<float, 4>
1005 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1006 #undef VIGRA_PIXELTYPE
1007 #define VIGRA_PIXELTYPE TinyVector<double, 2>
1008 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1009 #undef VIGRA_PIXELTYPE
1010 #define VIGRA_PIXELTYPE TinyVector<double, 3>
1011 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1012 #undef VIGRA_PIXELTYPE
1013 #define VIGRA_PIXELTYPE TinyVector<double, 4>
1014 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
1015 #undef VIGRA_PIXELTYPE
1016 
1017 #endif // NO_PARTIAL_TEMPLATE_SPECIALIZATION
1018 
1019 #undef VIGRA_DEFINE_ACCESSOR_TRAITS
1020 
1021 } // namespace vigra
1022 
1023 #endif // VIGRA_ACCESSOR_HXX
void setComponent(V const &value, ITERATOR const &i, int idx) const
Definition: accessor.hxx:799
Accessor for one component of a vector.
Definition: accessor.hxx:539
void set(V const &value, ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:585
VALUETYPE const & operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:283
VectorElementAccessor(int index, ACCESSOR a=ACCESSOR())
Definition: accessor.hxx:550
VectorComponentValueAccessor(int index)
Definition: accessor.hxx:459
void set(V const &value, ITERATOR const &i) const
Definition: accessor.hxx:398
void setComponent(V const &value, ITERATOR const &i, OFFSET const &diff, int idx) const
Definition: accessor.hxx:820
ACCESSOR::component_type value_type
Definition: accessor.hxx:546
VECTORTYPE::value_type value_type
Definition: accessor.hxx:371
void set(V value, ITERATOR const &i) const
Definition: accessor.hxx:228
value_type const & operator()(ITERATOR const &i) const
Definition: accessor.hxx:558
pair< typename Acc1::value_type, typename Acc2::value_type > value_type
Definition: accessor.hxx:878
component_type const & getComponent(ITERATOR const &i, OFFSET const &diff, int idx) const
Definition: accessor.hxx:808
Accessor for one component of a vector.
Definition: accessor.hxx:449
VALUETYPE value_type
Definition: accessor.hxx:138
VALUETYPE operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:219
iterator begin(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:672
void set(V value, ITERATOR const &i) const
Definition: accessor.hxx:488
Encapsulate access to the values an iterator points to.
Definition: accessor.hxx:307
value_type operator()(OFFSET1 d1, OFFSET2 const &d2) const
Definition: accessor.hxx:897
VECTORTYPE::value_type value_type
Definition: accessor.hxx:455
VALUETYPE operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:326
unsigned int size(ITERATOR const &i) const
Definition: accessor.hxx:689
value_type const & operator()(ITERATOR const &i) const
Definition: accessor.hxx:382
Accessor for items that are STL compatible vectors.
Definition: accessor.hxx:771
void set(V value, ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:242
void set(V const &value, ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:174
VALUETYPE value_type
Definition: accessor.hxx:203
VectorComponentAccessor(int index)
Definition: accessor.hxx:375
VECTOR::value_type component_type
Definition: accessor.hxx:777
Accessor for items that are STL compatible sequences.
Definition: accessor.hxx:632
void set(V value, ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:499
iterator begin(ITERATOR const &i) const
Definition: accessor.hxx:655
Encapsulate access to the values an iterator points to.
Definition: accessor.hxx:198
Access two images simultaneously.
Definition: accessor.hxx:871
void setIndex(int i)
Definition: accessor.hxx:416
value_type operator()(ITERATOR const &i) const
Definition: accessor.hxx:469
void setIndex(int i)
Definition: accessor.hxx:592
value_type const & operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:564
VectorElementAccessor< VectorAccessor< VECTOR > > ElementAccessor
Definition: accessor.hxx:782
Class for fixed size vectors.This class contains an array of size SIZE of the specified VALUETYPE...
Definition: accessor.hxx:940
iterator end(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:681
Accessor for one component of a vector.
Definition: accessor.hxx:365
value_type operator()(OFFSET const &d) const
Definition: accessor.hxx:889
VALUETYPE const & operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:150
void set(V const &value, ITERATOR const &i) const
Definition: accessor.hxx:160
Encapsulate read access to the values an iterator points to.
Definition: accessor.hxx:269
SEQUENCE::value_type component_type
Definition: accessor.hxx:638
value_type operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:478
VALUETYPE const & operator()(ITERATOR const &i) const
Definition: accessor.hxx:277
void set(V const &value, ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:409
VALUETYPE operator()(ITERATOR const &i) const
Definition: accessor.hxx:317
Class for a single RGB value.
Definition: accessor.hxx:938
Encapsulate access to the values an iterator points to.
Definition: accessor.hxx:133
component_type const & getComponent(ITERATOR const &i, int idx) const
Definition: accessor.hxx:788
MultiImageAccessor2(Iter1 i1, Acc1 a1, Iter2 i2, Acc2 a2)
Definition: accessor.hxx:882
void setIndex(int i)
Definition: accessor.hxx:506
VALUETYPE operator()(ITERATOR const &i) const
Definition: accessor.hxx:210
unsigned int size(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:694
void set(V const &value, ITERATOR const &i) const
Definition: accessor.hxx:574
value_type const & operator()(ITERATOR const &i, OFFSET const &diff) const
Definition: accessor.hxx:388
Definition: accessor.hxx:939
iterator end(ITERATOR const &i) const
Definition: accessor.hxx:663
VALUETYPE const & operator()(ITERATOR const &i) const
Definition: accessor.hxx:143

© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de)
Heidelberg Collaboratory for Image Processing, University of Heidelberg, Germany

html generated using doxygen and Python
vigra 1.11.1 (Fri May 19 2017)