BWAPI
|
00001 // Copyright (c) 2007 INRIA Sophia-Antipolis (France). 00002 // All rights reserved. 00003 // 00004 // This file is part of CGAL (www.cgal.org); you can redistribute it and/or 00005 // modify it under the terms of the GNU Lesser General Public License as 00006 // published by the Free Software Foundation; version 2.1 of the License. 00007 // See the file LICENSE.LGPL distributed with CGAL. 00008 // 00009 // Licensees holding a valid commercial license may use this file in 00010 // accordance with the commercial license agreement provided with the software. 00011 // 00012 // This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE 00013 // WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 00014 // 00015 // $URL: svn+ssh://scm.gforge.inria.fr/svn/cgal/branches/CGAL-3.5-branch/Spatial_sorting/include/CGAL/Hilbert_sort_3.h $ 00016 // $Id: Hilbert_sort_3.h 47102 2008-11-28 09:07:23Z spion $ 00017 // 00018 // Author(s) : Christophe Delage 00019 00020 #ifndef CGAL_HILBERT_SORT_3_H 00021 #define CGAL_HILBERT_SORT_3_H 00022 00023 #include <CGAL/basic.h> 00024 #include <functional> 00025 #include <cstddef> 00026 #include <CGAL/Hilbert_sort_base.h> 00027 00028 CGAL_BEGIN_NAMESPACE 00029 00030 namespace CGALi { 00031 template <class K, int x, bool up> struct Hilbert_cmp_3; 00032 00033 template <class K, int x> 00034 struct Hilbert_cmp_3<K,x,true> 00035 : public std::binary_function<typename K::Point_3, 00036 typename K::Point_3, bool> 00037 { 00038 typedef typename K::Point_3 Point; 00039 K k; 00040 Hilbert_cmp_3 (const K &_k = K()) : k(_k) {} 00041 bool operator() (const Point &p, const Point &q) const 00042 { 00043 return Hilbert_cmp_3<K,x,false> (k) (q, p); 00044 } 00045 }; 00046 00047 template <class K> 00048 struct Hilbert_cmp_3<K,0,false> 00049 : public std::binary_function<typename K::Point_3, 00050 typename K::Point_3, bool> 00051 { 00052 typedef typename K::Point_3 Point; 00053 K k; 00054 Hilbert_cmp_3 (const K &_k = K()) : k(_k) {} 00055 bool operator() (const Point &p, const Point &q) const 00056 { 00057 return k.less_x_3_object() (p, q); 00058 } 00059 }; 00060 00061 template <class K> 00062 struct Hilbert_cmp_3<K,1,false> 00063 : public std::binary_function<typename K::Point_3, 00064 typename K::Point_3, bool> 00065 { 00066 typedef typename K::Point_3 Point; 00067 K k; 00068 Hilbert_cmp_3 (const K &_k = K()) : k(_k) {} 00069 bool operator() (const Point &p, const Point &q) const 00070 { 00071 return k.less_y_3_object() (p, q); 00072 } 00073 }; 00074 00075 template <class K> 00076 struct Hilbert_cmp_3<K,2,false> 00077 : public std::binary_function<typename K::Point_3, 00078 typename K::Point_3, bool> 00079 { 00080 typedef typename K::Point_3 Point; 00081 K k; 00082 Hilbert_cmp_3 (const K &_k = K()) : k(_k) {} 00083 bool operator() (const Point &p, const Point &q) const 00084 { 00085 return k.less_z_3_object() (p, q); 00086 } 00087 }; 00088 } 00089 00090 template <class K> 00091 class Hilbert_sort_3 00092 { 00093 public: 00094 typedef K Kernel; 00095 typedef typename Kernel::Point_3 Point; 00096 00097 private: 00098 Kernel _k; 00099 std::ptrdiff_t _limit; 00100 00101 template <int x, bool up> struct Cmp : public CGALi::Hilbert_cmp_3<Kernel,x,up> 00102 { Cmp (const Kernel &k) : CGALi::Hilbert_cmp_3<Kernel,x,up> (k) {} }; 00103 00104 public: 00105 Hilbert_sort_3 (const Kernel &k = Kernel(), std::ptrdiff_t limit = 1) 00106 : _k(k), _limit (limit) 00107 {} 00108 00109 template <int x, bool upx, bool upy, bool upz, class RandomAccessIterator> 00110 void sort (RandomAccessIterator begin, RandomAccessIterator end) const 00111 { 00112 const int y = (x + 1) % 3, z = (x + 2) % 3; 00113 if (end - begin <= _limit) return; 00114 00115 RandomAccessIterator m0 = begin, m8 = end; 00116 00117 RandomAccessIterator m4 = CGALi::hilbert_split (m0, m8, Cmp< x, upx> (_k)); 00118 RandomAccessIterator m2 = CGALi::hilbert_split (m0, m4, Cmp< y, upy> (_k)); 00119 RandomAccessIterator m1 = CGALi::hilbert_split (m0, m2, Cmp< z, upz> (_k)); 00120 RandomAccessIterator m3 = CGALi::hilbert_split (m2, m4, Cmp< z, !upz> (_k)); 00121 RandomAccessIterator m6 = CGALi::hilbert_split (m4, m8, Cmp< y, !upy> (_k)); 00122 RandomAccessIterator m5 = CGALi::hilbert_split (m4, m6, Cmp< z, upz> (_k)); 00123 RandomAccessIterator m7 = CGALi::hilbert_split (m6, m8, Cmp< z, !upz> (_k)); 00124 00125 sort<z, upz, upx, upy> (m0, m1); 00126 sort<y, upy, upz, upx> (m1, m2); 00127 sort<y, upy, upz, upx> (m2, m3); 00128 sort<x, upx,!upy,!upz> (m3, m4); 00129 sort<x, upx,!upy,!upz> (m4, m5); 00130 sort<y,!upy, upz,!upx> (m5, m6); 00131 sort<y,!upy, upz,!upx> (m6, m7); 00132 sort<z,!upz,!upx, upy> (m7, m8); 00133 } 00134 00135 template <class RandomAccessIterator> 00136 void operator() (RandomAccessIterator begin, RandomAccessIterator end) const 00137 { 00138 sort <0, false, false, false> (begin, end); 00139 } 00140 }; 00141 00142 CGAL_END_NAMESPACE 00143 00144 #endif//CGAL_HILBERT_SORT_3_H