10 #ifndef EIGEN_RANDOMSETTER_H 11 #define EIGEN_RANDOMSETTER_H 13 #if defined(EIGEN_GOOGLEHASH_SUPPORT) 28 typedef std::map<KeyType,Scalar>
Type;
36 #ifdef EIGEN_UNORDERED_MAP_SUPPORT 53 template<
typename Scalar>
struct StdUnorderedMapTraits
56 typedef std::unordered_map<KeyType,Scalar>
Type;
61 static void setInvalidKey(Type&,
const KeyType&) {}
63 #endif // EIGEN_UNORDERED_MAP_SUPPORT 65 #if defined(EIGEN_GOOGLEHASH_SUPPORT) 71 using namespace ::google;
73 template<
typename KeyType,
typename Scalar>
75 typedef dense_hash_map<KeyType, Scalar>
type;
78 template<
typename KeyType,
typename Scalar>
79 struct SparseHashMap {
80 typedef sparse_hash_map<KeyType, Scalar>
type;
89 template<
typename Scalar>
struct GoogleDenseHashMapTraits
97 static void setInvalidKey(Type& map,
const KeyType& k)
98 { map.set_empty_key(k); }
105 template<
typename Scalar>
struct GoogleSparseHashMapTraits
113 static void setInvalidKey(Type&,
const KeyType&) {}
166 template<
typename SparseMatrixType,
167 template <
typename T>
class MapTraits =
168 #if defined(EIGEN_GOOGLEHASH_SUPPORT) 169 GoogleDenseHashMapTraits
170 #elif defined(_HASH_MAP) 175 ,
int OuterPacketBits = 6>
186 typedef typename MapTraits<ScalarWrapper>::KeyType
KeyType;
188 static const int OuterPacketMask = (1 << OuterPacketBits) - 1;
190 SwapStorage = 1 - MapTraits<ScalarWrapper>::IsSorted,
192 SetterRowMajor = SwapStorage ? 1-TargetRowMajor : TargetRowMajor
206 const Index outerSize = SwapStorage ? target.innerSize() : target.outerSize();
207 const Index innerSize = SwapStorage ? target.outerSize() : target.innerSize();
208 m_outerPackets = outerSize >> OuterPacketBits;
209 if (outerSize&OuterPacketMask)
211 m_hashmaps =
new HashMapType[m_outerPackets];
213 Index aux = innerSize - 1;
220 KeyType ik = (1<<(OuterPacketBits+m_keyBitsOffset));
221 for (
Index k=0; k<m_outerPackets; ++k)
222 MapTraits<ScalarWrapper>::setInvalidKey(m_hashmaps[k],ik);
225 for (
Index j=0;
j<mp_target->outerSize(); ++
j)
226 for (
typename SparseMatrixType::InnerIterator it(*mp_target,
j); it; ++it)
227 (*
this)(TargetRowMajor?
j:it.index(), TargetRowMajor?it.index():
j) = it.value();
233 KeyType keyBitsMask = (1<<m_keyBitsOffset)-1;
236 mp_target->setZero();
237 mp_target->makeCompressed();
238 mp_target->reserve(nonZeros());
239 Index prevOuter = -1;
240 for (
Index k=0; k<m_outerPackets; ++k)
242 const Index outerOffset = (1<<OuterPacketBits) * k;
243 typename HashMapType::iterator
end = m_hashmaps[k].end();
244 for (
typename HashMapType::iterator it = m_hashmaps[k].begin(); it!=
end; ++it)
246 const Index outer = (it->first >> m_keyBitsOffset) + outerOffset;
247 const Index inner = it->first & keyBitsMask;
248 if (prevOuter!=outer)
250 for (
Index j=prevOuter+1;
j<=outer;++
j)
251 mp_target->startVec(
j);
254 mp_target->insertBackByOuterInner(outer, inner) = it->second.value;
257 mp_target->finalize();
261 VectorXi positions(mp_target->outerSize());
264 for (
Index k=0; k<m_outerPackets; ++k)
266 typename HashMapType::iterator
end = m_hashmaps[k].end();
267 for (
typename HashMapType::iterator it = m_hashmaps[k].begin(); it!=
end; ++it)
269 const Index outer = it->first & keyBitsMask;
274 StorageIndex count = 0;
275 for (
Index j=0;
j<mp_target->outerSize(); ++
j)
277 StorageIndex tmp = positions[
j];
278 mp_target->outerIndexPtr()[
j] = count;
279 positions[
j] = count;
282 mp_target->makeCompressed();
283 mp_target->outerIndexPtr()[mp_target->outerSize()] = count;
284 mp_target->resizeNonZeros(count);
286 for (
Index k=0; k<m_outerPackets; ++k)
288 const Index outerOffset = (1<<OuterPacketBits) * k;
289 typename HashMapType::iterator
end = m_hashmaps[k].end();
290 for (
typename HashMapType::iterator it = m_hashmaps[k].begin(); it!=
end; ++it)
292 const Index inner = (it->first >> m_keyBitsOffset) + outerOffset;
293 const Index outer = it->first & keyBitsMask;
298 Index posStart = mp_target->outerIndexPtr()[outer];
299 Index i = (positions[outer]++) - 1;
300 while ( (i >= posStart) && (mp_target->innerIndexPtr()[
i] > inner) )
302 mp_target->valuePtr()[i+1] = mp_target->valuePtr()[
i];
303 mp_target->innerIndexPtr()[i+1] = mp_target->innerIndexPtr()[
i];
306 mp_target->innerIndexPtr()[i+1] = internal::convert_index<StorageIndex>(inner);
307 mp_target->valuePtr()[i+1] = it->second.value;
319 const Index outerMajor = outer >> OuterPacketBits;
320 const Index outerMinor = outer & OuterPacketMask;
321 const KeyType
key = internal::convert_index<KeyType>((outerMinor<<m_keyBitsOffset) | inner);
322 return m_hashmaps[outerMajor][
key].value;
333 for (
Index k=0; k<m_outerPackets; ++k)
334 nz += static_cast<Index>(m_hashmaps[k].
size());
349 #endif // EIGEN_RANDOMSETTER_H MapTraits< ScalarWrapper >::KeyType KeyType
const gtsam::Symbol key('X', 0)
RandomSetter(SparseMatrixType &target)
unsigned char m_keyBitsOffset
MapTraits< ScalarWrapper >::Type HashMapType
static void setInvalidKey(Type &, const KeyType &)
Namespace containing all symbols from the Eigen library.
SparseMatrixType::Scalar Scalar
const unsigned int RowMajorBit
SparseMatrixType::StorageIndex StorageIndex
EIGEN_DEFAULT_DENSE_INDEX_TYPE Index
The Index type as used for the API.
SparseMatrixType * mp_target
static EIGEN_DEPRECATED const end_t end
The RandomSetter is a wrapper object allowing to set/update a sparse matrix with random access...
internal::enable_if< internal::valid_indexed_view_overload< RowIndices, ColIndices >::value &&internal::traits< typename EIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::ReturnAsIndexedView, typename EIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::type operator()(const RowIndices &rowIndices, const ColIndices &colIndices) EIGEN_INDEXED_VIEW_METHOD_CONST
std::map< KeyType, Scalar > Type