VIGRA - vigra/accessor.hxx Source File

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

| vigra/accessor.hxx |
--- | --- | ---

    00001 /************************************************************************/
    00002 /*                                                                      */
    00003 /*               Copyright 1998-2002 by Ullrich Koethe                  */
    00004 /*       Cognitive Systems Group, University of Hamburg, Germany        */
    00005 /*                                                                      */
    00006 /*    This file is part of the VIGRA computer vision library.           */
    00007 /*    ( Version 1.5.0, Dec 07 2006 )                                    */
    00008 /*    The VIGRA Website is                                              */
    00009 /*        http://kogs-www.informatik.uni-hamburg.de/~koethe/vigra/      */
    00010 /*    Please direct questions, bug reports, and contributions to        */
    00011 /*        koethe@informatik.uni-hamburg.de          or                  */
    00012 /*        vigra@kogs1.informatik.uni-hamburg.de                         */
    00013 /*                                                                      */
    00014 /*    Permission is hereby granted, free of charge, to any person       */
    00015 /*    obtaining a copy of this software and associated documentation    */
    00016 /*    files (the "Software"), to deal in the Software without           */
    00017 /*    restriction, including without limitation the rights to use,      */
    00018 /*    copy, modify, merge, publish, distribute, sublicense, and/or      */
    00019 /*    sell copies of the Software, and to permit persons to whom the    */
    00020 /*    Software is furnished to do so, subject to the following          */
    00021 /*    conditions:                                                       */
    00022 /*                                                                      */
    00023 /*    The above copyright notice and this permission notice shall be    */
    00024 /*    included in all copies or substantial portions of the             */
    00025 /*    Software.                                                         */
    00026 /*                                                                      */
    00027 /*    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND    */
    00028 /*    EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES   */
    00029 /*    OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND          */
    00030 /*    NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT       */
    00031 /*    HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,      */
    00032 /*    WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING      */
    00033 /*    FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR     */
    00034 /*    OTHER DEALINGS IN THE SOFTWARE.                                   */
    00035 /*                                                                      */
    00036 /************************************************************************/
    00037
    00038 #ifndef VIGRA_ACCESSOR_HXX
    00039 #define VIGRA_ACCESSOR_HXX
    00040
    00041 #include "metaprogramming.hxx"
    00042 #include "numerictraits.hxx"
    00043 #include "tuple.hxx"
    00044
    00045 namespace vigra {
    00046
    00047 /** \addtogroup DataAccessors Data Accessors
    00048
    00049     Basic templates to encapsulate access to the data of an iterator.
    00050
    00051     Data accessors are used to allow for flexible access to the data
    00052     an iterator points to. When we access the data directly, we
    00053     are bound to what <TT>operator*()</TT> returns, if this method exists at
    00054     all. Encapsulating access in an accessor enables a better
    00055     decoupling of data structures and algorithms.
    00056     <a href="documents/DataAccessors.ps">This paper</a> contains
    00057     a detailed description of the concept. Here is a brief list of the basic
    00058     accessor requirements:
    00059 <p>
    00060 <table border=2 cellspacing=0 cellpadding=2 width="100%">
    00061 <tr><td>
    00062     \htmlonly
    00063     <th>
    00064     \endhtmlonly
    00065     Operation
    00066     \htmlonly
    00067     </th><th>
    00068     \endhtmlonly
    00069     Result
    00070     \htmlonly
    00071     </th><th>
    00072     \endhtmlonly
    00073     Semantics
    00074     \htmlonly
    00075     </th>
    00076     \endhtmlonly
    00077 </td></tr>
    00078 <tr>
    00079     <td><tt>accessor(iter)</tt></td><td>convertible to <br><tt>Iterator::value_type const &</tt></td>
    00080     <td>read data at the current position of the iterator</td>
    00081 </tr>
    00082 <tr>
    00083     <td><tt>accessor(iter, index)</tt></td><td>convertible to <br><tt>Accessor::value_type const &</tt></td>
    00084     <td>read data at offset <tt>index</tt> relative to iterator's current position
    00085     (random-access iterator only)</td>
    00086 </tr>
    00087 <tr>
    00088     <td><tt>accessor.set(value, iter)</tt></td><td><tt>void</tt></td>
    00089     <td>write data <tt>value</tt> at the current position of the iterator (mutable iterator only)</td>
    00090 </tr>
    00091 <tr>
    00092     <td><tt>accessor.set(value, iter, index)</tt></td><td><tt>void</tt></td>
    00093     <td>write data <tt>value</tt> at offset <tt>index</tt> relative to iterator's current position
    00094     (mutable random-access iterator only)</td>
    00095 </tr>
    00096 <tr>
    00097     <td>
    00098     \htmlonly
    00099     <td colspan=2>
    00100     \endhtmlonly
    00101     <tt>Accessor::value_type</tt></td>
    00102     <td>type of the data field the accessor refers to</td>
    00103 </tr>
    00104 <tr>
    00105     <td>
    00106     \htmlonly
    00107     <td colspan=3>
    00108     \endhtmlonly
    00109         <tt>iter</tt> is an iterator<br>
    00110         <tt>index</tt> has the iterator's index type (<tt>Iterator::difference_type</tt>)<br>
    00111         <tt>value</tt> is convertible to <tt>Accessor::value_type const &</tt>
    00112     </td>
    00113 </tr>
    00114 </table>
    00115 </p>
    00116
    00117     The template <tt>AccessorTraits&lt;T&gt;</tt> can be used to find the default accessor
    00118     associated with the type <tt>T</tt>, e.g.
    00119
    00120     \code
    00121     typedef typename AccessorTraits<typename Image::value_type>::default_accessor       Accessor;
    00122     typedef typename AccessorTraits<typename Image::value_type>::default_const_accessor ConstAccessor;
    00123     \endcode
    00124 */
    00125 //@{
    00126
    00127 /********************************************************/
    00128 /*                                                      */
    00129 /*                     StandardAccessor                 */
    00130 /*                                                      */
    00131 /********************************************************/
    00132
    00133 /** \brief Encapsulate access to the values an iterator points to.
    00134
    00135     StandardAccessor is a trivial accessor that simply encapsulates
    00136     the iterator's operator*() and operator[]() in its
    00137     read and write functions. It passes its arguments <em>by reference</em>.
    00138     If you want to return items by value, you
    00139     must use StandardValueAccessor instead of StandardAccessor.
    00140     Both accessors have different optimization properties --
    00141     StandardAccessor is usually faster for compound pixel types,
    00142     while StandardValueAccessor is faster for the built-in types.
    00143
    00144     When a floating point number is assigned by means of an accessor
    00145     with integral value_type, the value is rounded and clipped as approriate.
    00146
    00147     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00148     Namespace: vigra
    00149 */
    00150 template <class VALUETYPE>
    00151 class StandardAccessor
    00152 {
    00153   public:
    00154         /** the value_type
    00155         */
    00156     typedef VALUETYPE value_type;
    00157
    00158         /** read the current data item
    00159         */
    00160     template <class ITERATOR>
    00161     VALUETYPE const & operator()(ITERATOR const & i) const { return *i; }
    00162
    00163     VALUETYPE const & operator()(VALUETYPE const * i) const { return *i; }
    00164
    00165         /** read the data item at an offset (can be 1D or 2D or higher order difference).
    00166         */
    00167     template <class ITERATOR, class DIFFERENCE>
    00168     VALUETYPE const & operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00169     {
    00170         return i[diff];
    00171     }
    00172
    00173         /** Write the current data item. The type <TT>V</TT> of the passed
    00174             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
    00175             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00176         */
    00177     template <class V, class ITERATOR>
    00178     void set(V const & value, ITERATOR const & i) const
    00179     { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
    00180
    00181         /* This overload is needed to make the accessor work with a std::back_inserter */
    00182     template <class V, class ITERATOR>
    00183     void set(V const & value, ITERATOR & i) const
    00184     { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
    00185
    00186         /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
    00187             The type <TT>V</TT> of the passed
    00188             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
    00189             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00190         */
    00191     template <class V, class ITERATOR, class DIFFERENCE>
    00192     void set(V const & value, ITERATOR const & i, DIFFERENCE const & diff) const
    00193     {
    00194         i[diff]= detail::RequiresExplicitCast<VALUETYPE>::cast(value);
    00195     }
    00196 };
    00197
    00198 /** \brief Encapsulate access to the values an iterator points to.
    00199
    00200     StandardValueAccessor is a trivial accessor that simply encapsulates
    00201     the iterator's operator*() and operator[]() in its
    00202     read and write functions. It passes its arguments <em>by value</em>.
    00203     If the iterator returns its items by reference (such as \ref vigra::ImageIterator),
    00204     you can also use StandardAccessor.
    00205     These accessors have different optimization properties --
    00206     StandardAccessor is usually faster for compound pixel types,
    00207     while StandardValueAccessor is faster for the built-in types.
    00208
    00209     When a floating point number is assigned by means of an accessor
    00210     with integral value_type, the value is rounded and clipped as approriate.
    00211
    00212     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00213     Namespace: vigra
    00214 */
    00215 template <class VALUETYPE>
    00216 class StandardValueAccessor
    00217 {
    00218   public:
    00219         /** the value_type
    00220         */
    00221     typedef VALUETYPE value_type;
    00222
    00223         /** Read the current data item. The type <TT>ITERATOR::reference</TT>
    00224             is automatically converted to <TT>VALUETYPE</TT>.
    00225             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00226         */
    00227     template <class ITERATOR>
    00228     VALUETYPE operator()(ITERATOR const & i) const
    00229         { return detail::RequiresExplicitCast<VALUETYPE>::cast(*i); }
    00230
    00231         /** Read the data item at an offset (can be 1D or 2D or higher order difference).
    00232             The type <TT>ITERATOR::index_reference</TT>
    00233             is automatically converted to <TT>VALUETYPE</TT>.
    00234             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00235         */
    00236     template <class ITERATOR, class DIFFERENCE>
    00237     VALUETYPE operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00238     {
    00239         return detail::RequiresExplicitCast<VALUETYPE>::cast(i[diff]);
    00240     }
    00241         /** Write the current data item. The type <TT>V</TT> of the passed
    00242             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
    00243             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00244         */
    00245     template <class V, class ITERATOR>
    00246     void set(V value, ITERATOR const & i) const
    00247         { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
    00248
    00249         /* This overload is needed to make the accessor work with a std::back_inserter */
    00250     template <class V, class ITERATOR>
    00251     void set(V value, ITERATOR & i) const
    00252         { *i = detail::RequiresExplicitCast<VALUETYPE>::cast(value); }
    00253
    00254         /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
    00255             The type <TT>V</TT> of the passed
    00256             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
    00257             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00258         */
    00259     template <class V, class ITERATOR, class DIFFERENCE>
    00260     void set(V value, ITERATOR const & i, DIFFERENCE const & diff) const
    00261     {
    00262         i[diff]= detail::RequiresExplicitCast<VALUETYPE>::cast(value);
    00263     }
    00264 };
    00265
    00266 /********************************************************/
    00267 /*                                                      */
    00268 /*                StandardConstAccessor                 */
    00269 /*                                                      */
    00270 /********************************************************/
    00271
    00272 /** \brief Encapsulate read access to the values an iterator points to.
    00273
    00274     StandardConstAccessor is a trivial accessor that simply encapsulates
    00275     the iterator's operator*() and operator[]() in its
    00276     read functions. It passes its arguments <em>by reference</em>.
    00277     If the iterator returns its items by value (such as \ref vigra::CoordinateIterator), you
    00278     must use StandardConstValueAccessor instead of StandardConstAccessor.
    00279     Both accessors also have different optimization properties --
    00280     StandardConstAccessor is usually faster for compound pixel types,
    00281     while StandardConstValueAccessor is faster for the built-in types.
    00282
    00283     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00284     Namespace: vigra
    00285 */
    00286 template <class VALUETYPE>
    00287 class StandardConstAccessor
    00288 {
    00289   public:
    00290     typedef VALUETYPE value_type;
    00291
    00292         /** read the current data item
    00293         */
    00294     template <class ITERATOR>
    00295     VALUETYPE const & operator()(ITERATOR const & i) const
    00296         { return *i; }
    00297
    00298         /** read the data item at an offset (can be 1D or 2D or higher order difference).
    00299         */
    00300     template <class ITERATOR, class DIFFERENCE>
    00301     VALUETYPE const & operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00302     {
    00303         return i[diff];
    00304     }
    00305 };
    00306
    00307 /** \brief Encapsulate access to the values an iterator points to.
    00308
    00309     StandardConstValueAccessor is a trivial accessor that simply encapsulates
    00310     the iterator's operator*() and operator[]() in its
    00311     read functions. It passes its arguments <em>by value</em>.
    00312     If the iterator returns its items by reference (such as \ref vigra::ConstImageIterator),
    00313     you can also use StandardConstAccessor.
    00314     These accessors have different optimization properties --
    00315     StandardConstAccessor is usually faster for compound pixel types,
    00316     while StandardConstValueAccessor is faster for the built-in types.
    00317
    00318     When an iterator passes a floating point number to an accessor
    00319     with integral value_type, the value is rounded and clipped as approriate.
    00320
    00321     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00322     Namespace: vigra
    00323 */
    00324 template <class VALUETYPE>
    00325 class StandardConstValueAccessor
    00326 {
    00327   public:
    00328     typedef VALUETYPE value_type;
    00329
    00330         /** Read the current data item. The type <TT>ITERATOR::reference</TT>
    00331             is automatically converted to <TT>VALUETYPE</TT>.
    00332             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00333         */
    00334     template <class ITERATOR>
    00335     VALUETYPE operator()(ITERATOR const & i) const
    00336         { return detail::RequiresExplicitCast<VALUETYPE>::cast(*i); }
    00337
    00338         /** Read the data item at an offset (can be 1D or 2D or higher order difference).
    00339             The type <TT>ITERATOR::index_reference</TT>
    00340             is automatically converted to <TT>VALUETYPE</TT>.
    00341             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00342         */
    00343     template <class ITERATOR, class DIFFERENCE>
    00344     VALUETYPE operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00345     {
    00346         return detail::RequiresExplicitCast<VALUETYPE>::cast(i[diff]);
    00347     }
    00348 };
    00349
    00350 /********************************************************/
    00351 /*                                                      */
    00352 /*                 VectorComponentAccessor              */
    00353 /*                                                      */
    00354 /********************************************************/
    00355
    00356 /** \brief Accessor for one component of a vector.
    00357
    00358     This accessor allows to select a single component (a single 'band')
    00359     of a vector valued pixel type. The pixel type must support
    00360     <TT>operator[]</TT>. The index of the component to be selected
    00361     is passed in the constructor. The accessor returns its items
    00362     <em>by reference</em>. If you want to pass/return items by value,
    00363     use VectorComponentValueAccessor. If a floating point number
    00364     is assigned by means of an accessor with integral value_type, the
    00365     value is rounded and clipped as appropriate.
    00366
    00367     <b>Usage:</b>
    00368
    00369     \code
    00370     vigra::BRGBImage image(w,h);
    00371
    00372     // init red channel with 255
    00373     initImage(destImageRange(image,
    00374                              VectorComponentAccessor<vigra::BRGBImage::value_type>(0)),
    00375               255);
    00376     \endcode
    00377
    00378     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00379     Namespace: vigra
    00380
    00381 */
    00382 template <class VECTORTYPE>
    00383 class VectorComponentAccessor
    00384 {
    00385     int index_;
    00386   public:
    00387         /** the value_type
    00388         */
    00389     typedef typename VECTORTYPE::value_type value_type;
    00390
    00391         /** determine the component to be accessed
    00392         */
    00393     VectorComponentAccessor(int index)
    00394     : index_(index)
    00395     {}
    00396
    00397         /** read the current data item
    00398         */
    00399     template <class ITERATOR>
    00400     value_type const & operator()(ITERATOR const & i) const
    00401         { return (*i)[index_]; }
    00402
    00403         /** read the data item at an offset (can be 1D or 2D or higher order difference).
    00404         */
    00405     template <class ITERATOR, class DIFFERENCE>
    00406     value_type const & operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00407     {
    00408         return i[diff][index_];
    00409     }
    00410
    00411         /** Write the current data item. The type <TT>V</TT> of the passed
    00412             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00413             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00414         */
    00415     template <class V, class ITERATOR>
    00416     void set(V const & value, ITERATOR const & i) const
    00417     {
    00418         (*i)[index_] = detail::RequiresExplicitCast<value_type>::cast(value);
    00419     }
    00420
    00421         /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
    00422             The type <TT>V</TT> of the passed
    00423             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00424             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00425         */
    00426     template <class V, class ITERATOR, class DIFFERENCE>
    00427     void set(V const & value, ITERATOR const & i, DIFFERENCE const & diff) const
    00428     {
    00429         i[diff][index_]= detail::RequiresExplicitCast<value_type>::cast(value);
    00430     }
    00431
    00432         /** Reset the index to the given number.
    00433         */
    00434     void setIndex(int i)
    00435     {
    00436         index_ = i;
    00437     }
    00438 };
    00439
    00440 /** \brief Accessor for one component of a vector.
    00441
    00442     This accessor allows to select a single component (a single 'band')
    00443     of a vector valued pixel type. The pixel type must support
    00444     <TT>operator[]</TT>. The index of the component to be selected
    00445     is passed in the constructor. The accessor returns its items
    00446     <em>by value</em>. If you want to pass/return items by reference,
    00447     use VectorComponentAccessor. If a floating point number
    00448     is assigned by means of an accessor with integral value_type, the
    00449     value is rounded and clipped as appropriate.
    00450
    00451     <b>Usage:</b>
    00452
    00453     \code
    00454     vigra::BRGBImage image(w,h);
    00455
    00456     // init red channel with 255
    00457     initImage(destImageRange(image,
    00458                              VectorComponentValueAccessor<vigra::BRGBImage::value_type>(0)),
    00459               255);
    00460     \endcode
    00461
    00462     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00463     Namespace: vigra
    00464
    00465 */
    00466 template <class VECTORTYPE>
    00467 class VectorComponentValueAccessor
    00468 {
    00469     int index_;
    00470   public:
    00471         /** the value_type
    00472         */
    00473     typedef typename VECTORTYPE::value_type value_type;
    00474
    00475         /** determine the component to be accessed
    00476         */
    00477     VectorComponentValueAccessor(int index)
    00478     : index_(index)
    00479     {}
    00480
    00481         /** Read the current data item.
    00482             The type <TT>ITERATOR::index_reference::value_type</TT>
    00483             is automatically converted to <TT>value_type</TT>.
    00484             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00485         */
    00486     template <class ITERATOR>
    00487     value_type operator()(ITERATOR const & i) const
    00488         { return detail::RequiresExplicitCast<value_type>::cast((*i)[index_]); }
    00489
    00490         /** Read the data item at an offset (can be 1D or 2D or higher order difference).
    00491             The type <TT>ITERATOR::index_reference::value_type</TT>
    00492             is automatically converted to <TT>value_type</TT>.
    00493             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00494         */
    00495     template <class ITERATOR, class DIFFERENCE>
    00496     value_type operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00497     {
    00498         return detail::RequiresExplicitCast<value_type>::cast(i[diff][index_]);
    00499     }
    00500
    00501         /** Write the current data item. The type <TT>V</TT> of the passed
    00502             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00503             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00504         */
    00505     template <class V, class ITERATOR>
    00506     void set(V value, ITERATOR const & i) const
    00507     {
    00508         (*i)[index_] = detail::RequiresExplicitCast<value_type>::cast(value);
    00509     }
    00510
    00511         /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
    00512             The type <TT>V</TT> of the passed
    00513             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00514             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00515         */
    00516     template <class V, class ITERATOR, class DIFFERENCE>
    00517     void set(V value, ITERATOR const & i, DIFFERENCE const & diff) const
    00518     {
    00519         i[diff][index_]= detail::RequiresExplicitCast<value_type>::cast(value);
    00520     }
    00521
    00522         /** Reset the index to the given number.
    00523         */
    00524     void setIndex(int i)
    00525     {
    00526         index_ = i;
    00527     }
    00528 };
    00529
    00530 /********************************************************/
    00531 /*                                                      */
    00532 /*                   VectorElementAccessor              */
    00533 /*                                                      */
    00534 /********************************************************/
    00535
    00536 /** \brief Accessor for one component of a vector.
    00537
    00538     This works like VectorComponentAccessor, only the template paramters differ:
    00539     Here, we need a vector accessor type , wheras VectorComponentAccessor requires a vector type.
    00540
    00541     <b>Usage:</b>
    00542
    00543     \code
    00544     vigra::BRGBImage image(w,h);
    00545
    00546     // init red channel with 255
    00547     initImage(destImageRange(image,
    00548                              VectorElementAccessor<vigra::BRGBImage::Accessor>(0)),
    00549               255);
    00550     \endcode
    00551
    00552     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00553     Namespace: vigra
    00554
    00555 */
    00556 template <class ACCESSOR>
    00557 class VectorElementAccessor
    00558 {
    00559     int index_;
    00560     ACCESSOR a_;
    00561   public:
    00562         /** the value_type
    00563         */
    00564     typedef typename ACCESSOR::component_type value_type;
    00565
    00566         /** determine the component to be accessed
    00567         */
    00568     VectorElementAccessor(int index, ACCESSOR a = ACCESSOR())
    00569     : index_(index),
    00570       a_(a)
    00571     {}
    00572
    00573         /** read the current data item
    00574         */
    00575     template <class ITERATOR>
    00576     value_type const & operator()(ITERATOR const & i) const
    00577         { return a_.getComponent(i, index_); }
    00578
    00579         /** read the data item at an offset (can be 1D or 2D or higher order difference).
    00580         */
    00581     template <class ITERATOR, class DIFFERENCE>
    00582     value_type const & operator()(ITERATOR const & i, DIFFERENCE const & diff) const
    00583     {
    00584         return a_.getComponent(i, diff, index_);
    00585     }
    00586
    00587         /** Write the current data item. The type <TT>V</TT> of the passed
    00588             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00589             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00590         */
    00591     template <class V, class ITERATOR>
    00592     void set(V const & value, ITERATOR const & i) const
    00593     {
    00594         a_.setComponent(detail::RequiresExplicitCast<value_type>::cast(value), i, index_);
    00595     }
    00596
    00597         /** Write the data item at an offset (can be 1D or 2D or higher order difference)..
    00598             The type <TT>V</TT> of the passed
    00599             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
    00600             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00601         */
    00602     template <class V, class ITERATOR, class DIFFERENCE>
    00603     void set(V const & value, ITERATOR const & i, DIFFERENCE const & diff) const
    00604     {
    00605        a_.setComponent(detail::RequiresExplicitCast<value_type>::cast(value), i, diff, index_);
    00606     }
    00607
    00608         /** Reset the index to the given number.
    00609         */
    00610     void setIndex(int i)
    00611     {
    00612         index_ = i;
    00613     }
    00614 };
    00615
    00616 /********************************************************/
    00617 /*                                                      */
    00618 /*                    SequenceAccessor                  */
    00619 /*                                                      */
    00620 /********************************************************/
    00621
    00622 /** \brief Accessor for items that are STL compatible sequences.
    00623
    00624     It encapsulates access to the sequences' begin() and end()
    00625     functions.
    00626
    00627     <b>Usage:</b>
    00628
    00629     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00630     Namespace: vigra
    00631
    00632     \code
    00633     typedef std::list<std::list<int> > ListOfLists;
    00634
    00635     ListOfLists ll;
    00636     ...
    00637
    00638     typedef vigra::SequenceAccessor<ListOfLists::value_type> ListOfListsAccessor;
    00639     ListOfListsAccessor a;
    00640     for(ListOfLists::iterator li = ll.begin(); li != ll.end(); ++li)
    00641     {
    00642         for(ListOfListsAccessor::iterator i = a.begin(li); i != a.end(li); ++i)
    00643         {
    00644             *i = 10;
    00645         }
    00646     }
    00647     \endcode
    00648 */
    00649 template <class SEQUENCE>
    00650 class SequenceAccessor
    00651 : public StandardAccessor<SEQUENCE>
    00652 {
    00653   public:
    00654         /** the sequence's value_type
    00655         */
    00656     typedef typename SEQUENCE::value_type component_type;
    00657
    00658 #ifndef NO_PARTIAL_TEMPLATE_SPECIALIZATION
    00659     typedef typename
    00660             If<typename TypeTraits<SEQUENCE>::isConst,
    00661                typename SEQUENCE::const_iterator,
    00662                typename SEQUENCE::iterator>::type
    00663             iterator;
    00664 #else
    00665         /** the sequence's iterator type
    00666         */
    00667     typedef typename SEQUENCE::iterator iterator;
    00668 #endif
    00669
    00670         /** get begin iterator for sequence at given iterator position
    00671         */
    00672     template <class ITERATOR>
    00673     iterator begin(ITERATOR const & i) const
    00674     {
    00675         return (*i).begin();
    00676     }
    00677
    00678         /** get end iterator for sequence at given iterator position
    00679         */
    00680     template <class ITERATOR>
    00681     iterator end(ITERATOR const & i)  const
    00682     {
    00683          return (*i).end();
    00684     }
    00685
    00686         /** get begin iterator for sequence at an offset
    00687             of given iterator position
    00688         */
    00689     template <class ITERATOR, class DIFFERENCE>
    00690     iterator begin(ITERATOR const & i, DIFFERENCE const & diff)  const
    00691     {
    00692         return i[diff].begin();
    00693     }
    00694
    00695         /** get end iterator for sequence at a 2D difference vector
    00696             of given iterator position
    00697         */
    00698     template <class ITERATOR, class DIFFERENCE>
    00699     iterator end(ITERATOR const & i, DIFFERENCE const & diff)  const
    00700     {
    00701         return i[diff].end();
    00702     }
    00703
    00704         /** get size of sequence at given iterator position
    00705         */
    00706     template <class ITERATOR>
    00707     unsigned int size(ITERATOR const & i) const { return (*i).size(); }
    00708
    00709         /** get size of sequence at 2D difference vector of given iterator position
    00710         */
    00711     template <class ITERATOR, class DIFFERENCE>
    00712     unsigned int size(ITERATOR const & i, DIFFERENCE const & diff) const
    00713     { return i[diff].size(); }
    00714 };
    00715
    00716 /********************************************************/
    00717 /*                                                      */
    00718 /*                     VectorAccessor                   */
    00719 /*                                                      */
    00720 /********************************************************/
    00721
    00722 /** \brief Accessor for items that are STL compatible vectors.
    00723
    00724     It encapsulates access to a vector's access functionality.
    00725
    00726     <b> Usage:</b>
    00727
    00728     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00729     Namespace: vigra
    00730
    00731     The accessor has two modes of operation:
    00732
    00733     <ol>
    00734     <li> Access the vector's iterator via the <TT>begin()</TT> and <TT>end()</TT>
    00735     functions:
    00736
    00737     \code
    00738     typedef std::list<std::vector<int> > ListOfVectors;
    00739
    00740     ListOfVectors ll;
    00741     ...
    00742
    00743     typedef vigra::SequenceAccessor<ListOfVectors::value_type> ListOfVectorsAccessor;
    00744     ListOfVectorsAccessor a;
    00745     for(ListOfVectors::iterator li = ll.begin(); li != ll.end(); ++li)
    00746     {
    00747         for(ListOfVectorsAccessor::iterator i = a.begin(li); i != a.end(li); ++i)
    00748         {
    00749             *i = 10;
    00750         }
    00751     }
    00752     \endcode
    00753     <li> Access the vector's components via an index (internally calls
    00754     the vector's <TT>operator[]</TT> ):
    00755     \code
    00756     typedef std::list<std::vector<int> > ListOfVectors;
    00757
    00758     ListOfVectors ll;
    00759     ...
    00760
    00761     typedef vigra::SequenceAccessor<ListOfVectors::value_type> ListOfVectorsAccessor;
    00762     ListOfVectorsAccessor a;
    00763     for(ListOfVectors::iterator li = ll.begin(); li != ll.end(); ++li)
    00764     {
    00765         for(int i = 0; i != a.size(li); ++i)
    00766         {
    00767             a.setComponent(10, li, i);
    00768         }
    00769     }
    00770     \endcode
    00771     </ol>
    00772
    00773     <b> Required Interface:</b>
    00774
    00775     \code
    00776     VECTOR v;
    00777     VECTOR::iterator i;
    00778     value_type d;
    00779     int index;
    00780
    00781     d = v[index];
    00782     v[index] = d;
    00783     i = v.begin();
    00784     i = v.end();
    00785     v.size();
    00786     \endcode
    00787 */
    00788 template <class VECTOR>
    00789 class VectorAccessor
    00790 : public SequenceAccessor<VECTOR>
    00791 {
    00792   public:
    00793         /** the vector's value_type
    00794         */
    00795     typedef typename VECTOR::value_type component_type;
    00796
    00797         /** Read the component data at given vector index
    00798             at given iterator position
    00799         */
    00800     template <class ITERATOR>
    00801     component_type const & getComponent(ITERATOR const & i, int idx) const
    00802     {
    00803         return (*i)[idx];
    00804     }
    00805
    00806         /** Set the component data at given vector index
    00807             at given iterator position. The type <TT>V</TT> of the passed
    00808             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
    00809             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00810         */
    00811     template <class V, class ITERATOR>
    00812     void setComponent(V const & value, ITERATOR const & i, int idx) const
    00813     {
    00814         (*i)[idx] = detail::RequiresExplicitCast<component_type>::cast(value);
    00815     }
    00816
    00817         /** Read the component data at given vector index
    00818             at an offset of given iterator position
    00819         */
    00820     template <class ITERATOR, class DIFFERENCE>
    00821     component_type const & getComponent(ITERATOR const & i, DIFFERENCE const & diff, int idx) const
    00822     {
    00823         return i[diff][idx];
    00824     }
    00825
    00826     /** Set the component data at given vector index
    00827         at an offset of given iterator position. The type <TT>V</TT> of the passed
    00828         in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
    00829             In case of a conversion floating point -> intergral this includes rounding and clipping.
    00830     */
    00831     template <class V, class ITERATOR, class DIFFERENCE>
    00832     void
    00833     setComponent(V const & value, ITERATOR const & i, DIFFERENCE const & diff, int idx) const
    00834     {
    00835         i[diff][idx] = detail::RequiresExplicitCast<component_type>::cast(value);
    00836     }
    00837 };
    00838
    00839
    00840 /********************************************************/
    00841 /*                                                      */
    00842 /*                 MultiImageAccessor2                  */
    00843 /*                                                      */
    00844 /********************************************************/
    00845
    00846 /** \brief Access two images simultaneously.
    00847
    00848     This accessor is used when two images need to be treated as one
    00849     because an algorithm accepts only one image. For example,
    00850     \ref seededRegionGrowing() uses only one image two calculate
    00851     the cost for aggregating each pixel into a region. Somtimes, we
    00852     need more information to calcuate this cost, for example gray value
    00853     and local gradient magnitude. These values can be stored in two images,
    00854     which appear as only one when we pass a <TT>MultiImageAccessor2</TT> to
    00855     the lagorithms. Of course, the cost functor must accept a <TT>pair</TT>
    00856     of values for this to work. Instead of an actual image iterator, we
    00857     pass a <a href="CoordinateIterator.html">CoordinateIterator</a> which
    00858     selects the right pixels form both images.
    00859
    00860     <b> Usage:</b>
    00861
    00862     <b>\#include</b> "<a href="accessor_8hxx-source.html">vigra/accessor.hxx</a>"<br>
    00863     Namespace: vigra
    00864
    00865     \code
    00866     using namespace vigra;
    00867
    00868     FImage gray_values(w,h), gradient_magnitude(w,h);
    00869     IImage seeds(w,h), labels(w,h);
    00870
    00871     seededRegionGrowing(
    00872         srcIterRange(CoordinateIterator(), CoordinateIterator(w,h),
    00873            MultiImageAccessor2<FImage::iterator, FImage::Accessor,
    00874                                FImage::iterator, FImage::Accessor>
    00875                               (gray_values.upperLeft(), gray_values.accessor(),
    00876                                gradient_magnitude.upperLeft(), gradient_magnitude.accessor())),
    00877         srcImage(seeds),
    00878         destImage(labels),
    00879         SomeCostFunctor());
    00880     \endcode
    00881 */
    00882
    00883 template <class Iter1, class Acc1, class Iter2, class Acc2>
    00884 class MultiImageAccessor2
    00885 {
    00886   public:
    00887         /** The accessors value_type: construct a pair that contains
    00888             the corresponding image values.
    00889         */
    00890     typedef pair<typename Acc1::value_type, typename Acc2::value_type>
    00891             value_type;
    00892
    00893         /** Construct from two image iterators and associated accessors.
    00894         */
    00895     MultiImageAccessor2(Iter1 i1, Acc1 a1, Iter2 i2, Acc2 a2)
    00896     : i1_(i1), a1_(a1), i2_(i2), a2_(a2)
    00897     {}
    00898
    00899         /** read the current data item
    00900         */
    00901     template <class DIFFERENCE>
    00902     value_type operator()(DIFFERENCE const & d) const
    00903     {
    00904         return std::make_pair(a1_(i1_, d), a2_(i2_, d));
    00905     }
    00906
    00907         /** read the data item at an offset
    00908         */
    00909     template <class DIFFERENCE1, class DIFFERENCE2>
    00910     value_type operator()(DIFFERENCE1 d1, DIFFERENCE2 const & d2) const
    00911     {
    00912         d1 += d2;
    00913         return std::make_pair(a1_(i1_, d1), a2_(i2_, d1));
    00914     }
    00915
    00916   private:
    00917     Iter1 i1_;
    00918     Acc1 a1_;
    00919     Iter2 i2_;
    00920     Acc2 a2_;
    00921 };
    00922
    00923 //@}
    00924
    00925 template <class T>
    00926 struct AccessorTraits
    00927 {
    00928     typedef StandardAccessor<T>        default_accessor;
    00929     typedef StandardConstAccessor<T>   default_const_accessor;
    00930 };
    00931
    00932 #define VIGRA_DEFINE_ACCESSOR_TRAITS(VALUE, ACCESSOR, CONST_ACCESSOR) \
    00933     template <> \
    00934     struct AccessorTraits<VALUE > \
    00935     { \
    00936         typedef ACCESSOR<VALUE >         default_accessor; \
    00937         typedef CONST_ACCESSOR<VALUE >   default_const_accessor; \
    00938     };
    00939
    00940 VIGRA_DEFINE_ACCESSOR_TRAITS(signed char, StandardValueAccessor, StandardConstValueAccessor)
    00941 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned char, StandardValueAccessor, StandardConstValueAccessor)
    00942 VIGRA_DEFINE_ACCESSOR_TRAITS(short, StandardValueAccessor, StandardConstValueAccessor)
    00943 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned short, StandardValueAccessor, StandardConstValueAccessor)
    00944 VIGRA_DEFINE_ACCESSOR_TRAITS(int, StandardValueAccessor, StandardConstValueAccessor)
    00945 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned int, StandardValueAccessor, StandardConstValueAccessor)
    00946 VIGRA_DEFINE_ACCESSOR_TRAITS(long, StandardValueAccessor, StandardConstValueAccessor)
    00947 VIGRA_DEFINE_ACCESSOR_TRAITS(unsigned long, StandardValueAccessor, StandardConstValueAccessor)
    00948 VIGRA_DEFINE_ACCESSOR_TRAITS(float, StandardValueAccessor, StandardConstValueAccessor)
    00949 VIGRA_DEFINE_ACCESSOR_TRAITS(double, StandardValueAccessor, StandardConstValueAccessor)
    00950
    00951 template <class T, unsigned int RED_IDX, unsigned int GREEN_IDX, unsigned int BLUE_IDX> class RGBValue;
    00952 template <class T> class RGBAccessor;
    00953 template <class T, int SIZE> class TinyVector;
    00954
    00955 #ifndef NO_PARTIAL_TEMPLATE_SPECIALIZATION
    00956
    00957 template <class T, unsigned int RED_IDX, unsigned int GREEN_IDX, unsigned int BLUE_IDX>
    00958 struct AccessorTraits<RGBValue<T, RED_IDX, GREEN_IDX, BLUE_IDX> >
    00959 {
    00960     typedef RGBAccessor<RGBValue<T, RED_IDX, GREEN_IDX, BLUE_IDX> >   default_accessor;
    00961     typedef RGBAccessor<RGBValue<T, RED_IDX, GREEN_IDX, BLUE_IDX> >   default_const_accessor;
    00962 };
    00963
    00964 template <class T, int SIZE>
    00965 struct AccessorTraits<TinyVector<T, SIZE> >
    00966 {
    00967     typedef VectorAccessor<TinyVector<T, SIZE> >   default_accessor;
    00968     typedef VectorAccessor<TinyVector<T, SIZE> >   default_const_accessor;
    00969 };
    00970
    00971 #else // NO_PARTIAL_TEMPLATE_SPECIALIZATION
    00972
    00973 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned char>, RGBAccessor, RGBAccessor)
    00974 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<signed char>, RGBAccessor, RGBAccessor)
    00975 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<short>, RGBAccessor, RGBAccessor)
    00976 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned short>, RGBAccessor, RGBAccessor)
    00977 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<int>, RGBAccessor, RGBAccessor)
    00978 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned int>, RGBAccessor, RGBAccessor)
    00979 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<long>, RGBAccessor, RGBAccessor)
    00980 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<unsigned long>, RGBAccessor, RGBAccessor)
    00981 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<float>, RGBAccessor, RGBAccessor)
    00982 VIGRA_DEFINE_ACCESSOR_TRAITS(RGBValue<double>, RGBAccessor, RGBAccessor)
    00983
    00984 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 2>
    00985 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    00986 #undef VIGRA_PIXELTYPE
    00987 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 3>
    00988 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    00989 #undef VIGRA_PIXELTYPE
    00990 #define VIGRA_PIXELTYPE TinyVector<unsigned char, 4>
    00991 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    00992 #undef VIGRA_PIXELTYPE
    00993 #define VIGRA_PIXELTYPE TinyVector<short, 2>
    00994 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    00995 #undef VIGRA_PIXELTYPE
    00996 #define VIGRA_PIXELTYPE TinyVector<short, 3>
    00997 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    00998 #undef VIGRA_PIXELTYPE
    00999 #define VIGRA_PIXELTYPE TinyVector<short, 4>
    01000 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01001 #undef VIGRA_PIXELTYPE
    01002 #define VIGRA_PIXELTYPE TinyVector<int, 2>
    01003 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01004 #undef VIGRA_PIXELTYPE
    01005 #define VIGRA_PIXELTYPE TinyVector<int, 3>
    01006 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01007 #undef VIGRA_PIXELTYPE
    01008 #define VIGRA_PIXELTYPE TinyVector<int, 4>
    01009 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01010 #undef VIGRA_PIXELTYPE
    01011 #define VIGRA_PIXELTYPE TinyVector<float, 2>
    01012 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01013 #undef VIGRA_PIXELTYPE
    01014 #define VIGRA_PIXELTYPE TinyVector<float, 3>
    01015 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01016 #undef VIGRA_PIXELTYPE
    01017 #define VIGRA_PIXELTYPE TinyVector<float, 4>
    01018 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01019 #undef VIGRA_PIXELTYPE
    01020 #define VIGRA_PIXELTYPE TinyVector<double, 2>
    01021 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01022 #undef VIGRA_PIXELTYPE
    01023 #define VIGRA_PIXELTYPE TinyVector<double, 3>
    01024 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01025 #undef VIGRA_PIXELTYPE
    01026 #define VIGRA_PIXELTYPE TinyVector<double, 4>
    01027 VIGRA_DEFINE_ACCESSOR_TRAITS(VIGRA_PIXELTYPE, VectorAccessor, VectorAccessor)
    01028 #undef VIGRA_PIXELTYPE
    01029
    01030 #endif // NO_PARTIAL_TEMPLATE_SPECIALIZATION
    01031
    01032 #undef VIGRA_DEFINE_ACCESSOR_TRAITS
    01033
    01034 } // namespace vigra
    01035
    01036 #endif // VIGRA_ACCESSOR_HXX

© Ullrich Köthe (koethe@informatik.uni-hamburg.de) Cognitive Systems Group, University of Hamburg, Germany | html generated using doxygen and Python VIGRA 1.5.0 (7 Dec 2006)