Example #1
0
// Prepare a list of points for Delaunay triangulation: randomly assign into logarithmic bins, sort within bins, and add sentinels.
// For details, see Amenta et al., Incremental Constructions con BRIO.
static Array<Perturbed2> partially_sorted_shuffle(RawArray<const EV> Xin) {
  const int n = Xin.size();
  Array<Perturbed2> X(n+3,uninit);

  // Randomly assign input points into bins.  Bin k has 2**k = 1,2,4,8,... and starts at index 2**k-1 = 0,1,3,7,...
  // We fill points into bins as sequentially as possible to maximize cache coherence.
  const int bins = integer_log(n);
  Array<int> bin_counts(bins);
  for (int i=0;i<n;i++) {
    int j = (int)random_permute(n,key,i);
    const int bin = min(integer_log(j+1),bins-1);
    j = (1<<bin)-1+bin_counts[bin]++;
    X[j] = Perturbed2(i,Xin[i]);
  }

  // Spatially sort each bin down to clusters of size 64.
  const int leaf_size = 64;
  for (int bin=0;bin<bins;bin++) {
    const int start = (1<<bin)-1,
              end = bin==bins-1?n:start+(1<<bin);
    assert(bin_counts[bin]==end-start);
    spatial_sort(X.slice(start,end),leaf_size,new_<Random>(key+bin));
  }

  // Add 3 sentinel points at infinity
  X[n+0] = Perturbed2(n+0,EV(-bound,-bound));
  X[n+1] = Perturbed2(n+1,EV( bound, 0)    );
  X[n+2] = Perturbed2(n+2,EV(-bound, bound));

  return X;
}
Example #2
0
static void spatial_sort(RawArray<Perturbed2> X, const int leaf_size, Random& random) {
  const int n = X.size();
  if (n<=leaf_size)
    return;

  // We determine the subdivision axis using inexact computation, which is okay since neither the result nor
  // the asymptotic worst case complexity depends upon any properties of the spatial_sort whatsoever.
  const Box<EV> box = bounding_box(X.project<EV,&Perturbed2::value_>());
  const int axis = box.sizes().argmax();

  // We use exact arithmetic to perform the partition, which is important in case many points are coincident
  const int mid = axis==0 ? spatial_partition<0>(X,random)
                          : spatial_partition<1>(X,random);

  // Recursely sort both halves
  spatial_sort(X.slice(0,mid),leaf_size,random);
  spatial_sort(X.slice(mid,n),leaf_size,random);
}
Example #3
0
int main()
{

  std::vector<Point_3> points;
  Point_3 p;

  while(std::cin >> p){
    points.push_back(p);
  }
  Timer timer;
  timer.start();
  int N = 0;
  for(int i = 0; i < 5; i++){
    spatial_sort(points.begin(), points.end());
  }
  timer.stop();
  
  std::cerr << timer.time() << " sec" << std::endl;
  return 0;
}