All Distance Sketch  0.1
All distance sketch based algorithms
node_sketch.h
1 #ifndef SRC_SKETCH_NODE_SKETCH_H_
2 #define SRC_SKETCH_NODE_SKETCH_H_
3 
4 #include <math.h>
5 #include "../common.h"
6 #include "rank_calculator.h"
7 #if PROTO_BUF
8 #include "../proto/all_distance_sketch.pb.h"
9 #endif
10 
11 namespace all_distance_sketch {
14 typedef double RandomId;
15 
16 #if PROTO_BUF
17 typedef proto::AllDistanceSketchGpb AllDistanceSketchGpb;
18 typedef proto::AllDistanceSketchGpb::NodeThresholdGpb NodeThresholdGpb;
19 typedef proto::SingleNodeSketchGpb SingleNodeSketchGpb;
20 typedef proto::SingleNodeSketchGpb::NodeSummaryDetailsGpb NodeSummaryDetailsGpb;
21 typedef proto::SingleNodeSketchGpb::ZValuesGpb ZValuesGpb;
22 #endif
23 
27  public:
28  NodeIdDistanceData() {};
29  NodeIdDistanceData(int node_id, graph::EdgeWeight distance)
30  : node_id_(node_id), distance_(distance) {}
31 
32  inline int GetNId() const { return node_id_; }
33 
34  inline graph::EdgeWeight GetDistance() const { return distance_; }
35 
36  bool operator==(const NodeIdDistanceData& other) const{
37  return (GetNId() == other.GetNId()) &&
38  (GetDistance() == other.GetDistance());
39  }
40 
41  friend std::ostream& operator<<(std::ostream& os,
42  const NodeIdDistanceData& node_details) {
43  os << " NodeId=" << node_details.GetNId()
44  << " Distance=" << node_details.GetDistance();
45  return os;
46  }
47 
48  private:
49  int node_id_;
50  graph::EdgeWeight distance_;
51 };
52 
53 class NodeIdRandomIdData {
54  public:
55  NodeIdRandomIdData() {}
56  NodeIdRandomIdData(int node_id, RandomId random_id)
57  : node_id_(node_id), random_id_(random_id) {}
58  inline int GetNId() const { return node_id_; }
59 
60  inline RandomId GetRandomId() const { return random_id_; }
61 
62  private:
63  int node_id_;
64  RandomId random_id_;
65 };
66 
67 class NodeDistanceIdRandomIdData {
68  public:
69  NodeDistanceIdRandomIdData() {}
70  NodeDistanceIdRandomIdData(NodeIdRandomIdData aDetails,
71  graph::EdgeWeight distance)
72  : details(aDetails), distance_(distance) {}
73 
74  NodeDistanceIdRandomIdData(graph::EdgeWeight distance, int node_id,
75  RandomId random_id)
76  : details(node_id, random_id), distance_(distance) {}
77 
78  inline graph::EdgeWeight GetDistance() const { return distance_; }
79 
80  inline int GetNId() const { return details.GetNId(); }
81 
82  inline RandomId GetRandomId() const { return details.GetRandomId(); }
83 
84  inline const NodeIdRandomIdData& GetDetails() { return details; }
85 
86  bool operator==(const NodeDistanceIdRandomIdData& other) const {
87  return (GetNId() == other.GetNId()) &&
88  (GetRandomId() == other.GetRandomId()) &&
89  (GetDistance() == other.GetDistance());
90  }
91 
92  friend std::ostream& operator<<(std::ostream& os,
93  const NodeDistanceIdRandomIdData& node_details) {
94  os << " NodeId=" << node_details.GetNId()
95  << " Distance=" << node_details.GetDistance()
96  << " HashId=" << node_details.GetRandomId();
97  return os;
98  }
99 
100  private:
101  NodeIdRandomIdData details;
102  graph::EdgeWeight distance_;
103 };
104 
105 struct compare_node_randomid_decreasing {
106  bool operator()(const NodeDistanceIdRandomIdData& n1,
107  const NodeDistanceIdRandomIdData& n2) const {
108  return n1.GetRandomId() < n2.GetRandomId();
109  }
110 };
111 
112 struct compare_node_distance_increasing {
113  bool operator()(const NodeIdDistanceData& n1,
114  const NodeIdDistanceData& n2) const {
115  return n1.GetDistance() > n2.GetDistance();
116  }
117 };
118 
119 struct compare_node_distance_decreasing {
120  bool operator()(const NodeIdDistanceData& n1,
121  const NodeIdDistanceData& n2) const {
122  return n1.GetDistance() < n2.GetDistance();
123  }
124 };
125 
126 class Neighbourhood {
127  public:
128  Neighbourhood() {}
129  Neighbourhood(int distance, int size) : distance_(distance), size_(size) {}
130 
131  int GetSize() const { return size_; }
132 
133  int GetDistance() const { return distance_; }
134 
135  bool operator==(const Neighbourhood& other) const {
136  return (GetSize() == other.GetSize()) &&
137  (GetDistance() == other.GetDistance());
138  }
139 
140 
141  private:
142  int distance_;
143  int size_;
144 };
145 
146 struct compare_neighbourhood_distance {
147  bool operator()(const Neighbourhood& n1, const Neighbourhood& n2) const {
148  return n1.GetDistance() < n2.GetDistance();
149  }
150 };
151 
152 struct compare_neighbourhood_size {
153  bool operator()(const Neighbourhood& n1, const Neighbourhood& n2) const {
154  return n1.GetSize() < n2.GetSize();
155  }
156 };
157 
158 class PrunningThreshold {
159  public:
160  PrunningThreshold()
161  : is_distance_equal_to_following_node_distance_in_ads(false),
162  distance_(constants::UNREACHABLE) {}
163 
164  graph::EdgeWeight GetDistance() const { return distance_; }
165 
166  void SetDistance(graph::EdgeWeight distance) { distance_ = distance; }
167 
168  bool GetIsEqualToNext() const {
169  return is_distance_equal_to_following_node_distance_in_ads;
170  }
171 
172  void SetIsEqualToNext(bool aIsEqual) {
173  is_distance_equal_to_following_node_distance_in_ads = aIsEqual;
174  }
175  bool operator==(const PrunningThreshold& other) const {
176  return GetDistance() == other.GetDistance();
177  }
178 
179  private:
180  bool is_distance_equal_to_following_node_distance_in_ads;
181  graph::EdgeWeight distance_;
182 };
183 
184 typedef struct NodeProb_t {
185  double prob;
186  int node_id;
187 } NodeProb;
188 
189 typedef std::vector<Neighbourhood> NeighbourhoodVector;
190 typedef std::unordered_map<graph::EdgeWeight, NodeIdDistanceData> ZValues;
193 typedef std::vector<NodeIdDistanceData> NodeIdDistanceVector;
196 typedef std::vector<NodeIdDistanceData>::iterator NodeIdDistanceVectorItr;
197 typedef std::vector<NodeDistanceIdRandomIdData>
198  NodeDistanceIdRandomIdDataVector;
199 typedef std::vector<NodeDistanceIdRandomIdData>::iterator
200  NodeDistanceIdRandomIdDataVectorItr;
201 
204 class NodeSketch {
205  public:
208  NodeSketch() { was_init_ = false; }
209 
210  void InitNodeSketch(
211  int K, int node_id, RandomId random_id,
212  std::vector<PrunningThreshold>* prunning_thresholds = NULL,
213  unsigned int reserve_size = 1,
214  bool should_calc_z_value = false) {
215  K_ = K;
216  node_id_ = node_id;
217  random_id_ = random_id;
218  was_init_ = true;
219  nodes_id_distance_.clear();
220  prunning_thresholds_ = prunning_thresholds;
221  should_calc_z_value_ = should_calc_z_value;
222  }
223 
224  bool IsInit() const { return was_init_; }
225 
226  bool AddToCandidates(NodeDistanceIdRandomIdData node_details) {
227  candidate_nodes_.push_back(node_details);
228  return true;
229  }
230 
231  int InsertCandidatesNodes() {
232  compare_node_randomid_decreasing obj;
233  sort(candidate_nodes_.begin(), candidate_nodes_.end(), obj);
234  // Sort according to random ID.
235  for (unsigned int i = 0; i < candidate_nodes_.size(); i++) {
236  Add(candidate_nodes_[i]);
237  }
238  int numInserted = candidate_nodes_.size();
239  candidate_nodes_.clear();
240  return numInserted;
241  }
242 
243  bool Add(NodeDistanceIdRandomIdData node_details) {
244  NodeIdDistanceData node_id_distance(node_details.GetNId(),
245  node_details.GetDistance());
246  return Add(node_id_distance);
247  }
248 
249  void ShouldInsert(NodeIdDistanceData node_details, bool* should_insert,
250  bool* is_zvalue) {
251  NodeIdDistanceVector::reverse_iterator it_k =
252  nodes_id_distance_.rbegin() + (K_ - 1);
253 
254  if (node_details.GetDistance() > it_k->GetDistance()) {
255  (*is_zvalue) = false;
256  (*should_insert) = false;
257  return;
258  }
259  if (node_details.GetDistance() == it_k->GetDistance()) {
260  if (z_values_.find(node_details.GetDistance()) != z_values_.end()) {
261  (*should_insert) = false;
262  (*is_zvalue) = false;
263  } else {
264  (*should_insert) = false;
265  (*is_zvalue) = true;
266  }
267  return;
268  }
269  (*should_insert) = true;
270  (*is_zvalue) = false;
271  return;
272  }
273 
274  bool Add(NodeIdDistanceData node_details) {
275  // If the NodeSketch size is smaller than K we will always add
276 
277  if (nodes_id_distance_.size() < K_) {
278  LOG_M(DEBUG4, " Adding to NodeSketch since size < k, "
279  << " size=" << nodes_id_distance_.size()
280  << " k=" << K_);
281  // nodes_id_distance_.push_back(node_details);
282  compare_node_distance_increasing obj;
283  NodeIdDistanceVectorItr up =
284  std::upper_bound(nodes_id_distance_.begin(),
285  nodes_id_distance_.end(), node_details, obj);
286  nodes_id_distance_.insert(up, node_details);
287  return true;
288  }
289 
290  // Are you Z value?
291  bool is_z_value;
292  bool should_insert;
293  ShouldInsert(node_details, &should_insert, &is_z_value);
294 
295  if (is_z_value) {
296  z_values_.insert(
297  std::make_pair(node_details.GetDistance(), node_details));
298  return false;
299  }
300 
301  if (!should_insert) {
302  return false;
303  }
304 
305  // Size of the vector is bigger than K
306  // The vector is sorted according to distance
307  // Checking if distnace is inside the possible distance
308  compare_node_distance_decreasing obj;
309 
310  NodeIdDistanceVector::reverse_iterator up = std::upper_bound(
311  nodes_id_distance_.rbegin(), nodes_id_distance_.rbegin() + K_,
312  node_details, obj);
313  unsigned int position_upper = up - nodes_id_distance_.rbegin();
314 
315  LOG_M(DEBUG4, " Size of array "
316  << nodes_id_distance_.size()
317  << " upper position=" << position_upper
318  << " up=" << *(up) << " First element "
319  << nodes_id_distance_[0] << " Last element "
320  << nodes_id_distance_[nodes_id_distance_.size() - 1]);
321 
322  /*
323  if (position_upper > K_) {
324  LOG_M(NOTICE," Distance of node=" << node_details.GetDistance() <<
325  " K threshold=" << (nodes_id_distance_.rbegin() + (K_ -
326  1))->GetDistance());
327  return false;
328  }
329  */
330 
331  LOG_M(DEBUG5, "Before inserting");
332 
333  if (position_upper <= K_) {
334  unsigned int position_relative_to_begin =
335  nodes_id_distance_.rend() - up;
336  NodeIdDistanceVectorItr it;
337  if (position_relative_to_begin == nodes_id_distance_.size()) {
338  it = nodes_id_distance_.end();
339  } else {
340  it = nodes_id_distance_.begin() + position_relative_to_begin;
341  }
342  nodes_id_distance_.insert(it, node_details);
343  LOG_M(DEBUG4, " Inserting to NodeSketch at location "
344  << position_relative_to_begin);
345  if (prunning_thresholds_ != NULL) {
346  (*prunning_thresholds_)[node_id_].SetDistance(
347  (nodes_id_distance_.rbegin() + (K_ - 1))->GetDistance());
348  if (nodes_id_distance_.size() >= K_) {
349  bool is_distance_equal_to_following_node_distance_in_ads =
350  ((nodes_id_distance_.rbegin() + (K_ - 1))->GetDistance() ==
351  (nodes_id_distance_.rbegin() + (K_))->GetDistance());
352  (*prunning_thresholds_)[node_id_].SetIsEqualToNext(
353  is_distance_equal_to_following_node_distance_in_ads);
354  }
355  }
356 
357  return true;
358  }
359 
360  return false;
361  }
362 
363  void Get(graph::EdgeWeight distance,
364  NodeIdDistanceVector* nodes_id_distance_vector) {
365  nodes_id_distance_vector->clear();
366  for (NodeIdDistanceVector::reverse_iterator iter =
367  nodes_id_distance_.rbegin();
368  iter != nodes_id_distance_.rend(); iter++) {
369  if (iter->GetDistance() <= distance) {
370  LOG_M(DEBUG5, "Inserting to vector node " << *iter);
371  nodes_id_distance_vector->push_back(*(iter));
372  }
373  }
374  }
375 
376  void GetAllDistances(NodeIdDistanceVector* nodes_id_distance_vector) {
377  nodes_id_distance_vector->clear();
378  *nodes_id_distance_vector = nodes_id_distance_;
379  }
382  int GetSketchSize() { return nodes_id_distance_.size(); }
385  /*
386  * What is the distance such that all |nodes < distance| >= neighborhood_size
387  */
388  double GetDistanceCoverNeighborhood(int neighborhood_size) {
389  compare_neighbourhood_size obj;
390  Neighbourhood entry(0, neighborhood_size);
391  NeighbourhoodVector::iterator up = std::upper_bound(
392  neighbourhoods_.begin(), neighbourhoods_.end(), entry, obj);
393 
394  if (neighbourhoods_.size() == 0) {
395  LOG_M(DEBUG3, "neighbourhoods vector is empty, returning 0");
396  return 0;
397  }
398  if (up == neighbourhoods_.begin()) {
399  LOG_M(DEBUG3, "Match first element");
400  if (up->GetSize() == neighbourhoods_.begin()->GetSize()) {
401  return up->GetDistance();
402  }
403  return 0;
404  }
405  if (up == neighbourhoods_.end()) {
406  LOG_M(DEBUG3, "Match last element");
407  return neighbourhoods_.back().GetDistance() + 1;
408  }
409  LOG_M(DEBUG3, " Distance= " << up->GetDistance() <<
410  " Size=" << up->GetSize() <<
411  " Wanted size=" << neighborhood_size);
412  return up->GetDistance();
413  }
414  /*
415  * Gets the first distance index such that the distance is <= distance
416  */
417  int GetNeighborhoodDistanceIndex(graph::EdgeWeight distance) {
418  compare_neighbourhood_distance obj;
419  Neighbourhood entry(distance, 0);
420  NeighbourhoodVector::iterator up = std::upper_bound(
421  neighbourhoods_.begin(), neighbourhoods_.end(), entry, obj);
422  if (neighbourhoods_.size() == 0) {
423  return -1;
424  }
425  if (up == neighbourhoods_.begin()) {
426  if (up->GetDistance() == neighbourhoods_.begin()->GetDistance()) {
427  return 0;
428  }
429  // The distance is smaller than the smallest distance
430  return -1;
431  }
432  if (up == neighbourhoods_.end()) {
433  return neighbourhoods_.size() - 1;
434  }
435  if (up->GetDistance() > distance) {
436  up -= 1;
437  }
438  return up - neighbourhoods_.begin();
439  }
440 
441  // Case fail -1
442  double GetNeighborhoodDistanceByIndex(int index) {
443  if (index < 0) {
444  return 0;
445  }
446  if (index >= neighbourhoods_.size()) {
447  return neighbourhoods_.back().GetSize();
448  }
449  return (neighbourhoods_.begin() + index)->GetSize();
450  }
451 
452  /*
453  * Return the size of the neighborhood <= distance
454  */
455  int GetSizeNeighborhoodUpToDistance(graph::EdgeWeight distance) {
456  compare_neighbourhood_distance obj;
457  Neighbourhood entry(distance, 0);
458  NeighbourhoodVector::iterator up = std::upper_bound(
459  neighbourhoods_.begin(), neighbourhoods_.end(), entry, obj);
460 
461  if (up == neighbourhoods_.begin()) {
462  LOG_M(DEBUG3, "Distance is in the begin of the vector" <<
463  " Distance= " << up->GetDistance() <<
464  " Size=" << up->GetSize());
465  if (up->GetDistance() == neighbourhoods_.begin()->GetDistance()) {
466  return up->GetSize();
467  }
468  // The distance is smaller than the smallest distance
469  return 0;
470  }
471 
472  if (up == neighbourhoods_.end()) {
473  LOG_M(DEBUG3, "Distance is in the end of the vector" <<
474  " Size=" << neighbourhoods_.back().GetSize());
475  return neighbourhoods_.back().GetSize();
476  }
477  if (up->GetDistance() > distance) {
478  up -= 1;
479  }
480  LOG_M(DEBUG3, "Distance is in the midddle of the vector" <<
481  " Distance= " << up->GetDistance() <<
482  " Size=" << up->GetSize());
483  return up->GetSize();
484  }
485  /*
486  * Calculate for each distance the neighborhood size.
487  */
488  void CalculateAllDistanceNeighborhood() {
489  neighbourhoods_.clear();
490  if (nodes_id_distance_.size() == 0) {
491  return;
492  }
493 
494  std::vector<NodeDistanceIdRandomIdData> neighborhoodVector;
495  NodeIdDistanceVector::reverse_iterator it;
496  neighbourhoods_.clear();
497  unsigned int currentDistance = 0;
498  compare_node_randomid_decreasing obj;
499  for (it = nodes_id_distance_.rbegin(); it != nodes_id_distance_.rend();
500  it++) {
501  LOG_M(DEBUG3, "Iterting " << *it << " Current distance=" << currentDistance);
502  if (it->GetDistance() != currentDistance) {
503  LOG_M(DEBUG3, " Changing distance to " << it->GetDistance());
504  // Calculate neighbour
505  int size = 0;
506  if (neighborhoodVector.size() < K_) {
507  if (neighborhoodVector.size() == 0) {
508  size = 0;
509  } else {
510  size = neighborhoodVector.size() - 1;
511  }
512  } else {
513  RandomId omega = neighborhoodVector[K_ - 1].GetRandomId();
514  size = (K_ - 1) / omega;
515  }
516  LOG_M(DEBUG3, " Size of neighborhood " << size);
517  Neighbourhood entry(currentDistance, size);
518  neighbourhoods_.push_back(entry);
519  currentDistance = it->GetDistance();
520  }
521 
522  NodeDistanceIdRandomIdData t(it->GetDistance(), it->GetNId(),
523  (*node_distribution_)[it->GetNId()]);
524  std::vector<NodeDistanceIdRandomIdData>::iterator up =
525  std::upper_bound(neighborhoodVector.begin(),
526  neighborhoodVector.end(), t, obj);
527  neighborhoodVector.insert(up, t);
528  }
529 
530  // Another iteration for the last element
531  int size;
532  if (neighborhoodVector.size() < K_) {
533  if (neighborhoodVector.size() == 0) {
534  size = 0;
535  } else {
536  size = neighborhoodVector.size() - 1;
537  }
538 
539  } else {
540  RandomId omega = neighborhoodVector[K_ - 1].GetRandomId();
541  size = (K_ - 1) / omega;
542  }
543  Neighbourhood entry(nodes_id_distance_.begin()->GetDistance(), size);
544  neighbourhoods_.push_back(entry);
545  }
546 
547  NeighbourhoodVector* UTGetNeighbourhoodVector() { return &neighbourhoods_; }
548 
549  NodeIdDistanceVector* UTGetNodeAdsVector() { return &nodes_id_distance_; }
550  void SetPrunningThresholds(std::vector<PrunningThreshold>* athresholds) {
551  prunning_thresholds_ = athresholds;
552  }
555  const NodeIdDistanceVector* GetNodeAdsVector() const {
556  return &nodes_id_distance_;
557  }
558 
559  int GetK() const { return K_; }
560 
561  int GetNId() const { return node_id_; }
562 
563  RandomId GetRandomId() const { return random_id_; }
564 
567  const NeighbourhoodVector& GetNeighbourHoodVector() const {
568  return neighbourhoods_;
569  }
570 
571  const std::vector<NodeDistanceIdRandomIdData>& GetCandidates() const {
572  return candidate_nodes_;
573  }
574 
575  bool operator==(const NodeSketch& other) const {
576  if (IsInit() == false && other.IsInit() == false) {
577  return true;
578  }
579  if (GetK() != other.GetK()) {
580  LOG_M(NOTICE, " K is not euqal!" <<
581  " lhs K = " << GetK() <<
582  " rhs K = " << other.GetK());
583  return false;
584  }
585 
586  if (GetNId() != other.GetNId()) {
587  LOG_M(NOTICE, " Node id is not equal!");
588  return false;
589  }
590 
591  if (GetRandomId() != other.GetRandomId()) {
592  LOG_M(NOTICE, " RandomId is not equal!");
593  }
594  if (*GetNodeAdsVector() != (*other.GetNodeAdsVector())) {
595  LOG_M(NOTICE, " Node Sketches are not equal!");
596  return false;
597  }
598  if (GetNeighbourHoodVector() != other.GetNeighbourHoodVector()) {
599  LOG_M(NOTICE, " NeighbourHood Vector are not equal!");
600  return false;
601  }
602  if (GetCandidates() != other.GetCandidates()) {
603  LOG_M(NOTICE, " Candidates Vector are not equal!");
604  return false;
605  }
606  return true;
607  }
610  const ZValues& GetZValues() { return z_values_; }
611 
612  bool HasZValue(graph::EdgeWeight distance) {
613  return z_values_.find(distance) != z_values_.end();
614  }
615 
616  void set_z_values(ZValues* z) {
617  z_values_ = *z;
618  }
619 
620  void CalculateInsertProb(std::vector<NodeProb>* insert_prob) {
621  // Easy case - All nodes insert thus the threshold is 1 for all
622  insert_prob->clear();
623  if (nodes_id_distance_.size() < K_) {
624  for (int i = 0; i < nodes_id_distance_.size(); i++) {
625  NodeProb node_thresh_prob;
626  node_thresh_prob.prob = 1;
627  node_thresh_prob.node_id = nodes_id_distance_[i].GetNId();
628  insert_prob->push_back(node_thresh_prob);
629  }
630  return;
631  }
632  // Any node below this distance gets automatic entrence thus prob == 1
633  std::vector<NodeDistanceIdRandomIdData> moving_threshold;
634  graph::EdgeWeight distance_covered = -1;
635  compare_node_randomid_decreasing comparator;
636  for (NodeIdDistanceVector::reverse_iterator r_it =
637  nodes_id_distance_.rbegin();
638  r_it < nodes_id_distance_.rend(); r_it++) {
639  LOG_M(DEBUG3,
640  "id:" << r_it->GetNId() << " distane:" << r_it->GetDistance()
641  << " random id: " << (*node_distribution_)[r_it->GetNId()]);
642 
643  if (distance_covered != r_it->GetDistance()) {
644  for (NodeIdDistanceVector::reverse_iterator runner_it = r_it;
645  (runner_it->GetDistance() == r_it->GetDistance()) &&
646  runner_it != nodes_id_distance_.rend();
647  runner_it++) {
648  NodeDistanceIdRandomIdData node_details(
649  runner_it->GetDistance(), runner_it->GetNId(),
650  (*node_distribution_)[runner_it->GetNId()]);
651 
652  moving_threshold.insert(std::upper_bound(moving_threshold.begin(),
653  moving_threshold.end(),
654  node_details,
655  comparator),
656  node_details);
657  }
658  // Is there Z value?
659  ZValues::iterator z_it = z_values_.find(r_it->GetDistance());
660  if (z_it != z_values_.end()) {
661  NodeDistanceIdRandomIdData node_details(
662  z_it->second.GetDistance(), z_it->second.GetNId(),
663  (*node_distribution_)[z_it->second.GetNId()]);
664 
665  moving_threshold.insert(std::upper_bound(moving_threshold.begin(),
666  moving_threshold.end(),
667  node_details,
668  comparator),
669  node_details);
670  }
671 
672  distance_covered = r_it->GetDistance();
673  }
674  NodeProb node_thresh_prob;
675  node_thresh_prob.node_id = r_it->GetNId();
676  if (moving_threshold.size() <= K_) {
677  LOG_M(DEBUG3, "node id:" << r_it->GetNId() << " prob: 1");
678  node_thresh_prob.prob = 1;
679  } else {
680  std::vector<NodeDistanceIdRandomIdData>::iterator it_k_plus_1 =
681  moving_threshold.begin() + K_;
682  if (node_thresh_prob.node_id == it_k_plus_1->GetNId()) {
683  // This is Z value! not one of the K smallest!
684  // We don't want to consider
685  LOG_M(DEBUG3, " node id:" << r_it->GetNId() << " Skip Z value");
686  continue;
687  }
688  node_thresh_prob.prob = it_k_plus_1->GetRandomId();
689  }
690  insert_prob->push_back(node_thresh_prob);
691  }
692  std::reverse(insert_prob->begin(), insert_prob->end());
693  }
694 
695  void SetDisribution(std::vector<RandomId>* node_distribution) {
696  node_distribution_ = node_distribution;
697  }
700  NodeIdDistanceVectorItr Begin() {
701  return nodes_id_distance_.begin();
702  }
703 
704  NodeIdDistanceVectorItr End() {
705  return nodes_id_distance_.end();
706  }
707 
708 private:
709  friend class GraphSketch;
710  bool was_init_;
711  bool should_calc_z_value_;
712  unsigned int K_;
713  int node_id_;
714  std::vector<RandomId>* node_distribution_;
715  RandomId random_id_;
716  NodeIdDistanceVector nodes_id_distance_;
717  std::vector<NodeDistanceIdRandomIdData> candidate_nodes_;
718  std::vector<PrunningThreshold>* prunning_thresholds_;
719  NeighbourhoodVector neighbourhoods_;
720  ZValues z_values_;
721 };
722 
723 
724 } // namespace all_distance_sketch
725 
726 #endif // SRC_SKETCH_NODE_SKETCH_H_
Single node sketch.
Definition: node_sketch.h:204
Definition: common.h:53
std::vector< NodeIdDistanceData >::iterator NodeIdDistanceVectorItr
Definition: node_sketch.h:196
std::vector< NodeIdDistanceData > NodeIdDistanceVector
Container for node id and distance.
Definition: node_sketch.h:193
const float UNREACHABLE
Definition: common.h:62
Data structure for the graph sketch.
Definition: graph_sketch.h:17
double RandomId
Type for random ids.
Definition: node_sketch.h:14
Container class to store node id and distance.
Definition: node_sketch.h:26