12 #ifndef __RD_SPARSE_INT_VECT_20070921__
13 #define __RD_SPARSE_INT_VECT_20070921__
27 template <
typename IndexType>
39 d_length = other.d_length;
40 d_data.insert(other.d_data.begin(), other.d_data.end());
45 initFromText(pkl.c_str(), pkl.size());
49 initFromText(pkl, len);
56 #pragma clang diagnostic push
57 #pragma clang diagnostic ignored "-Wtautological-compare"
58 #elif (defined(__GNUC__) || defined(__GNUG__)) && \
59 (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ > 1))
60 #if (__GNUC__ > 4 || __GNUC_MINOR__ > 5)
61 #pragma GCC diagnostic push
63 #pragma GCC diagnostic ignored "-Wtype-limits"
67 if (idx < 0 || idx >= d_length) {
71 typename StorageType::const_iterator iter = d_data.find(idx);
72 if (iter != d_data.end()) {
79 void setVal(IndexType idx,
int val) {
80 if (idx < 0 || idx >= d_length) {
90 #pragma clang diagnostic pop
91 #elif (defined(__GNUC__) || defined(__GNUG__)) && \
92 (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ > 5))
93 #pragma GCC diagnostic pop
105 typename StorageType::const_iterator iter;
106 for (iter = d_data.begin(); iter != d_data.end(); ++iter) {
110 res += abs(iter->second);
124 if (other.d_length != d_length) {
128 typename StorageType::iterator iter = d_data.begin();
129 typename StorageType::const_iterator oIter = other.d_data.begin();
130 while (iter != d_data.end()) {
132 while (oIter != other.d_data.end() && oIter->first < iter->first) {
135 if (oIter != other.d_data.end() && oIter->first == iter->first) {
137 if (oIter->second < iter->second) {
138 iter->second = oIter->second;
145 typename StorageType::iterator tmpIter = iter;
163 if (other.d_length != d_length) {
167 typename StorageType::iterator iter = d_data.begin();
168 typename StorageType::const_iterator oIter = other.d_data.begin();
169 while (iter != d_data.end()) {
171 while (oIter != other.d_data.end() && oIter->first < iter->first) {
172 d_data[oIter->first] = oIter->second;
175 if (oIter != other.d_data.end() && oIter->first == iter->first) {
177 if (oIter->second > iter->second) {
178 iter->second = oIter->second;
185 while (oIter != other.d_data.end()) {
186 d_data[oIter->first] = oIter->second;
198 if (other.d_length != d_length) {
201 typename StorageType::iterator iter = d_data.begin();
202 typename StorageType::const_iterator oIter = other.d_data.begin();
203 while (oIter != other.d_data.end()) {
204 while (iter != d_data.end() && iter->first < oIter->first) {
207 if (iter != d_data.end() && oIter->first == iter->first) {
209 iter->second += oIter->second;
211 typename StorageType::iterator tIter = iter;
219 d_data[oIter->first] = oIter->second;
232 if (other.d_length != d_length) {
235 typename StorageType::iterator iter = d_data.begin();
236 typename StorageType::const_iterator oIter = other.d_data.begin();
237 while (oIter != other.d_data.end()) {
238 while (iter != d_data.end() && iter->first < oIter->first) {
241 if (iter != d_data.end() && oIter->first == iter->first) {
243 iter->second -= oIter->second;
245 typename StorageType::iterator tIter = iter;
253 d_data[oIter->first] = -oIter->second;
265 typename StorageType::iterator iter = d_data.begin();
266 while (iter != d_data.end()) {
277 typename StorageType::iterator iter = d_data.begin();
278 while (iter != d_data.end()) {
289 typename StorageType::iterator iter = d_data.begin();
290 while (iter != d_data.end()) {
301 typename StorageType::iterator iter = d_data.begin();
302 while (iter != d_data.end()) {
314 if (d_length != v2.d_length) {
317 return d_data == v2.d_data;
320 return !(*
this == v2);
325 std::stringstream ss(std::ios_base::binary | std::ios_base::out |
330 tInt =
sizeof(IndexType);
333 IndexType nEntries = d_data.size();
336 typename StorageType::const_iterator iter = d_data.begin();
337 while (iter != d_data.end()) {
339 std::int32_t tInt = iter->second;
347 initFromText(txt.c_str(), txt.length());
354 void initFromText(
const char *pkl,
const unsigned int len) {
356 std::stringstream ss(std::ios_base::binary | std::ios_base::out |
362 if (vers == 0x0001) {
365 if (tInt >
sizeof(IndexType)) {
367 "IndexType cannot accomodate index size in SparseIntVect pickle");
371 readVals<unsigned char>(ss);
373 case sizeof(std::int32_t):
374 readVals<std::uint32_t>(ss);
376 case sizeof(boost::int64_t):
377 readVals<boost::uint64_t>(ss);
386 template <
typename T>
387 void readVals(std::stringstream &ss) {
388 PRECONDITION(
sizeof(T) <=
sizeof(IndexType),
"invalid size");
394 for (T i = 0; i < nEntries; ++i) {
403 template <
typename IndexType,
typename SequenceType>
405 const SequenceType &seq) {
406 typename SequenceType::const_iterator seqIt;
407 for (seqIt = seq.begin(); seqIt != seq.end(); ++seqIt) {
409 IndexType idx = *seqIt;
415 template <
typename IndexType>
416 void calcVectParams(
const SparseIntVect<IndexType> &v1,
417 const SparseIntVect<IndexType> &v2,
double &v1Sum,
418 double &v2Sum,
double &andSum) {
419 if (v1.getLength() != v2.getLength()) {
422 v1Sum = v2Sum = andSum = 0.0;
425 typename SparseIntVect<IndexType>::StorageType::const_iterator iter1, iter2;
426 iter1 = v1.getNonzeroElements().begin();
427 if (iter1 != v1.getNonzeroElements().end()) v1Sum += abs(iter1->second);
428 iter2 = v2.getNonzeroElements().begin();
429 if (iter2 != v2.getNonzeroElements().end()) v2Sum += abs(iter2->second);
430 while (iter1 != v1.getNonzeroElements().end()) {
431 while (iter2 != v2.getNonzeroElements().end() &&
432 iter2->first < iter1->first) {
434 if (iter2 != v2.getNonzeroElements().end()) v2Sum += abs(iter2->second);
436 if (iter2 != v2.getNonzeroElements().end()) {
437 if (iter2->first == iter1->first) {
438 if (abs(iter2->second) < abs(iter1->second)) {
439 andSum += abs(iter2->second);
441 andSum += abs(iter1->second);
444 if (iter2 != v2.getNonzeroElements().end()) v2Sum += abs(iter2->second);
447 if (iter1 != v1.getNonzeroElements().end()) v1Sum += abs(iter1->second);
452 if (iter1 != v1.getNonzeroElements().end()) {
454 while (iter1 != v1.getNonzeroElements().end()) {
455 v1Sum += abs(iter1->second);
459 if (iter2 != v2.getNonzeroElements().end()) {
461 while (iter2 != v2.getNonzeroElements().end()) {
462 v2Sum += abs(iter2->second);
469 template <
typename IndexType>
472 bool returnDistance =
false,
double bounds = 0.0) {
478 if (!returnDistance && bounds > 0.0) {
481 double denom = v1Sum + v2Sum;
482 if (fabs(denom) < 1e-6) {
483 if (returnDistance) {
489 double minV = v1Sum < v2Sum ? v1Sum : v2Sum;
490 if (2. * minV / denom < bounds) {
499 calcVectParams(v1, v2, v1Sum, v2Sum, numer);
501 double denom = v1Sum + v2Sum;
503 if (fabs(denom) < 1e-6) {
506 sim = 2. * numer / denom;
508 if (returnDistance) sim = 1. - sim;
513 template <
typename IndexType>
516 bool returnDistance =
false,
double bounds = 0.0) {
525 calcVectParams(v1, v2, v1Sum, v2Sum, andSum);
527 double denom = a * v1Sum + b * v2Sum + (1 - a - b) * andSum;
530 if (fabs(denom) < 1e-6) {
533 sim = andSum / denom;
535 if (returnDistance) sim = 1. - sim;
540 template <
typename IndexType>
543 bool returnDistance =
false,
double bounds = 0.0) {