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 itkNeighborhood_hxx
19 #define itkNeighborhood_hxx
20
21 #include "itkNeighborhood.h"
22 #include "itkNumericTraits.h"
23
24 namespace itk
25 {
26 template< typename TPixel, unsigned int VDimension, typename TContainer >
27 void
28 Neighborhood< TPixel, VDimension, TContainer >
ComputeNeighborhoodStrideTable()29 ::ComputeNeighborhoodStrideTable()
30 {
31 for ( DimensionValueType dim = 0; dim < VDimension; ++dim )
32 {
33 OffsetValueType stride = 0;
34 OffsetValueType accum = 1;
35
36 for ( DimensionValueType i = 0; i < VDimension; ++i )
37 {
38 if ( i == dim ) { stride = accum; }
39 accum *= m_Size[i];
40 }
41
42 m_StrideTable[dim] = stride;
43 }
44 }
45
46 template< typename TPixel, unsigned int VDimension, typename TContainer >
47 void Neighborhood< TPixel, VDimension, TContainer >
ComputeNeighborhoodOffsetTable()48 ::ComputeNeighborhoodOffsetTable()
49 {
50 m_OffsetTable.clear();
51 m_OffsetTable.reserve( this->Size() );
52 OffsetType o;
53 DimensionValueType i, j;
54 for ( j = 0; j < VDimension; j++ )
55 {
56 o[j] = -( static_cast< OffsetValueType >( this->GetRadius(j) ) );
57 }
58
59 for ( i = 0; i < this->Size(); ++i )
60 {
61 m_OffsetTable.push_back(o);
62 for ( j = 0; j < VDimension; j++ )
63 {
64 o[j] = o[j] + 1;
65 if ( o[j] > static_cast< OffsetValueType >( this->GetRadius(j) ) )
66 {
67 o[j] = -( static_cast< OffsetValueType >( this->GetRadius(j) ) );
68 }
69 else { break; }
70 }
71 }
72 }
73
74 template< typename TPixel, unsigned int VDimension, typename TContainer >
75 void
76 Neighborhood< TPixel, VDimension, TContainer >
SetRadius(const SizeValueType s)77 ::SetRadius(const SizeValueType s)
78 {
79 SizeType k;
80
81 for ( DimensionValueType i = 0; i < VDimension; i++ )
82 {
83 k[i] = s;
84 }
85 this->SetRadius(k);
86 }
87
88 template< typename TPixel, unsigned int VDimension, typename TContainer >
89 void
90 Neighborhood< TPixel, VDimension, TContainer >
SetRadius(const SizeType & r)91 ::SetRadius(const SizeType & r)
92 {
93 this->m_Radius = r;
94 this->SetSize();
95
96 SizeValueType cumul = NumericTraits< SizeValueType >::OneValue();
97 for ( DimensionValueType i = 0; i < VDimension; i++ )
98 {
99 cumul *= m_Size[i];
100 }
101
102 this->Allocate(cumul);
103 this->ComputeNeighborhoodStrideTable();
104 this->ComputeNeighborhoodOffsetTable();
105 }
106
107 template< typename TPixel, unsigned int VDimension, typename TContainer >
108 Neighborhood< TPixel, VDimension, TContainer >
Neighborhood(const Self & other)109 ::Neighborhood(const Self & other):
110 m_Radius ( other.m_Radius ),
111 m_Size ( other.m_Size ),
112 m_DataBuffer ( other.m_DataBuffer ),
113 m_OffsetTable( other.m_OffsetTable )
114 {
115 std::copy(other.m_StrideTable,
116 other.m_StrideTable+VDimension,
117 m_StrideTable);
118 }
119
120 template< typename TPixel, unsigned int VDimension, typename TContainer >
121 Neighborhood< TPixel, VDimension, TContainer > &
122 Neighborhood< TPixel, VDimension, TContainer >
operator =(const Self & other)123 ::operator=(const Self & other)
124 {
125 if(this != &other)
126 {
127 m_Radius = other.m_Radius;
128 m_Size = other.m_Size;
129 m_DataBuffer = other.m_DataBuffer;
130 std::copy(other.m_StrideTable,
131 other.m_StrideTable+VDimension,
132 m_StrideTable);
133 m_OffsetTable = other.m_OffsetTable;
134 }
135 return *this;
136 }
137
138 template< typename TPixel, unsigned int VDimension, typename TContainer >
139 std::slice Neighborhood< TPixel, VDimension, TContainer >
GetSlice(unsigned int d) const140 ::GetSlice(unsigned int d) const
141 {
142 const OffsetValueType t = this->GetStride(d);
143 const auto s = static_cast< OffsetValueType >( this->GetSize()[d] );
144
145 OffsetValueType n = this->Size() / 2;
146 n -= t * s / 2;
147
148 return { static_cast< size_t >( n ),
149 static_cast< size_t >( s ),
150 static_cast< size_t >( t ) };
151 }
152
153 template< typename TPixel, unsigned int VDimension, typename TContainer >
154 typename Neighborhood< TPixel, VDimension, TContainer >::NeighborIndexType
155 Neighborhood< TPixel, VDimension, TContainer >
GetNeighborhoodIndex(const OffsetType & o) const156 ::GetNeighborhoodIndex(const OffsetType & o) const
157 {
158 unsigned int idx = ( this->Size() / 2 );
159
160 for ( unsigned i = 0; i < VDimension; ++i )
161 {
162 idx += o[i] * m_StrideTable[i];
163 }
164 return idx;
165 }
166
167 template< typename TPixel, unsigned int VDimension, typename TContainer >
168 void Neighborhood< TPixel, VDimension, TContainer >
PrintSelf(std::ostream & os,Indent indent) const169 ::PrintSelf(std::ostream & os, Indent indent) const
170 {
171 os << indent << "m_Size: [ ";
172 for (DimensionValueType i = 0; i < VDimension; ++i )
173 {
174 os << m_Size[i] << " ";
175 }
176 os << "]" << std::endl;
177
178 os << indent << "m_Radius: [ ";
179 for (DimensionValueType i = 0; i < VDimension; ++i )
180 {
181 os << m_Radius[i] << " ";
182 }
183 os << "]" << std::endl;
184
185 os << indent << "m_StrideTable: [ ";
186 for (DimensionValueType i = 0; i < VDimension; ++i )
187 {
188 os << m_StrideTable[i] << " ";
189 }
190 os << "]" << std::endl;
191
192 os << indent << "m_OffsetTable: [ ";
193 for (DimensionValueType i = 0; i < m_OffsetTable.size(); ++i )
194 {
195 os << m_OffsetTable[i] << " ";
196 }
197 os << "]" << std::endl;
198 }
199 } // namespace itk
200
201 #endif
202