1 /*=========================================================================
2  *
3  *  Copyright Insight Software Consortium
4  *
5  *  Licensed under the Apache License, Version 2.0 (the "License");
6  *  you may not use this file except in compliance with the License.
7  *  You may obtain a copy of the License at
8  *
9  *         http://www.apache.org/licenses/LICENSE-2.0.txt
10  *
11  *  Unless required by applicable law or agreed to in writing, software
12  *  distributed under the License is distributed on an "AS IS" BASIS,
13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  *  See the License for the specific language governing permissions and
15  *  limitations under the License.
16  *
17  *=========================================================================*/
18 #ifndef itkCovariantVector_hxx
19 #define itkCovariantVector_hxx
20 
21 #include "itkCovariantVector.h"
22 #include "itkMath.h"
23 #include "itkNumericTraits.h"
24 
25 namespace itk
26 {
27 template< typename T, unsigned int TVectorDimension >
28 CovariantVector< T, TVectorDimension >
CovariantVector(const ValueType & r)29 ::CovariantVector(const ValueType & r)
30 {
31   for ( typename BaseArray::Iterator i = BaseArray::Begin(); i != BaseArray::End(); ++i )
32     {
33     *i = r;
34     }
35 }
36 
37 template< typename T, unsigned int NVectorDimension >
38 CovariantVector< T, NVectorDimension > &
39 CovariantVector< T, NVectorDimension >
operator =(const ValueType r[NVectorDimension])40 ::operator=(const ValueType r[NVectorDimension])
41 {
42   BaseArray::operator=(r);
43   return *this;
44 }
45 
46 template< typename T, unsigned int NVectorDimension >
47 const typename CovariantVector< T, NVectorDimension >::Self &
48 CovariantVector< T, NVectorDimension >
operator +=(const Self & vec)49 ::operator+=(const Self & vec)
50 {
51   for ( unsigned int i = 0; i < NVectorDimension; i++ )
52     {
53     ( *this )[i] += vec[i];
54     }
55   return *this;
56 }
57 
58 template< typename T, unsigned int NVectorDimension >
59 const typename CovariantVector< T, NVectorDimension >::Self &
60 CovariantVector< T, NVectorDimension >
operator -=(const Self & vec)61 ::operator-=(const Self & vec)
62 {
63   for ( unsigned int i = 0; i < NVectorDimension; i++ )
64     {
65     ( *this )[i] -= vec[i];
66     }
67   return *this;
68 }
69 
70 template< typename T, unsigned int NVectorDimension >
71 CovariantVector< T, NVectorDimension >
72 CovariantVector< T, NVectorDimension >
operator -() const73 ::operator-() const
74 {
75   Self result;
76 
77   for ( unsigned int i = 0; i < NVectorDimension; i++ )
78     {
79     result[i] = -( *this )[i];
80     }
81   return result;
82 }
83 
84 template< typename T, unsigned int NVectorDimension >
85 typename CovariantVector< T, NVectorDimension >::Self
86 CovariantVector< T, NVectorDimension >
operator +(const Self & vec) const87 ::operator+(const Self & vec) const
88 {
89   Self result;
90 
91   for ( unsigned int i = 0; i < NVectorDimension; i++ )
92     {
93     result[i] = ( *this )[i] + vec[i];
94     }
95   return result;
96 }
97 
98 template< typename T, unsigned int NVectorDimension >
99 typename CovariantVector< T, NVectorDimension >::Self
100 CovariantVector< T, NVectorDimension >
operator -(const Self & vec) const101 ::operator-(const Self & vec)  const
102 {
103   Self result;
104 
105   for ( unsigned int i = 0; i < NVectorDimension; i++ )
106     {
107     result[i] = ( *this )[i] - vec[i];
108     }
109   return result;
110 }
111 
112 template< typename T, unsigned int NVectorDimension >
113 typename CovariantVector< T, NVectorDimension >::ValueType
114 CovariantVector< T, NVectorDimension >
operator *(const Self & other) const115 ::operator*(const Self & other) const
116 {
117   typename NumericTraits< T >::AccumulateType value = NumericTraits< T >::ZeroValue();
118   for ( unsigned int i = 0; i < NVectorDimension; i++ )
119     {
120     value += ( *this )[i] * other[i];
121     }
122   return static_cast< ValueType >( value );
123 }
124 
125 template< typename T, unsigned int NVectorDimension >
126 typename CovariantVector< T, NVectorDimension >::ValueType
127 CovariantVector< T, NVectorDimension >
operator *(const Vector<T,NVectorDimension> & other) const128 ::operator*(const Vector< T, NVectorDimension > & other) const
129 {
130   typename NumericTraits< T >::AccumulateType value = NumericTraits< T >::ZeroValue();
131   for ( unsigned int i = 0; i < NVectorDimension; i++ )
132     {
133     value += ( *this )[i] * other[i];
134     }
135   return value;
136 }
137 
138 template< typename T, unsigned int NVectorDimension >
139 typename CovariantVector< T, NVectorDimension >::RealValueType
140 CovariantVector< T, NVectorDimension >
GetSquaredNorm() const141 ::GetSquaredNorm() const
142 {
143   RealValueType sum = NumericTraits< RealValueType >::ZeroValue();
144 
145   for ( unsigned int i = 0; i < NVectorDimension; i++ )
146     {
147     const RealValueType value = ( *this )[i];
148     sum += value * value;
149     }
150   return sum;
151 }
152 
153 template< typename T, unsigned int NVectorDimension >
154 typename CovariantVector< T, NVectorDimension >::RealValueType
155 CovariantVector< T, NVectorDimension >
GetNorm() const156 ::GetNorm() const
157 {
158   return std::sqrt( this->GetSquaredNorm() );
159 }
160 
161 template< typename T, unsigned int NVectorDimension >
162 typename CovariantVector< T, NVectorDimension >::RealValueType
163 CovariantVector< T, NVectorDimension >
Normalize()164 ::Normalize()
165 {
166   const RealValueType norm = this->GetNorm();
167 
168   for ( unsigned int i = 0; i < NVectorDimension; i++ )
169     {
170     ( *this )[i] /= norm;
171     }
172 
173   return norm;
174 }
175 
176 template< typename T, unsigned int NVectorDimension >
177 void
178 CovariantVector< T, NVectorDimension >
SetVnlVector(const vnl_vector<T> & v)179 ::SetVnlVector(const vnl_vector< T > & v)
180 {
181   for ( unsigned int i = 0; i < v.size(); i++ )
182     {
183     ( *this )[i] = v(i);
184     }
185 }
186 
187 template< typename T, unsigned int NVectorDimension >
188 vnl_vector_ref< T >
189 CovariantVector< T, NVectorDimension >
GetVnlVector()190 ::GetVnlVector()
191 {
192   return vnl_vector_ref< T >( NVectorDimension, this->GetDataPointer() );
193 }
194 
195 template< typename T, unsigned int NVectorDimension >
196 vnl_vector< T >
197 CovariantVector< T, NVectorDimension >
GetVnlVector() const198 ::GetVnlVector() const
199 {
200   // Return a vector_ref<>.  This will be automatically converted to a
201   // vnl_vector<>.  We have to use a const_cast<> which would normally
202   // be prohibited in a const method, but it is safe to do here
203   // because the cast to vnl_vector<> will ultimately copy the data.
204   return vnl_vector_ref< T >( NVectorDimension,
205                               const_cast< T * >( this->GetDataPointer() ) );
206 }
207 
208 } // end namespace itk
209 
210 #endif
211