C++ STL源码剖析
1 1. // Filename: stl_config.h 2 2. 3 3. // Comment By: 凝霜 4 4. // E-mail: mdl2009@vip.qq.com 5 5. // Blog: http://blog.csdn.net/mdl13412 6 6. 7 7. /* 8 8. * Copyright (c) 1996-1997 9 9. * Silicon Graphics Computer Systems, Inc. 10 10. * 11 11. * Permission to use, copy, modify, distribute and sell this software 12 12. * and its documentation for any purpose is hereby granted without fee, 13 13. * provided that the above copyright notice appear in all copies and 14 14. * that both that copyright notice and this permission notice appear 15 15. * in supporting documentation. Silicon Graphics makes no 16 16. * representations about the suitability of this software for any 17 17. * purpose. It is provided "as is" without express or implied warranty. 18 18. */ 19 19. 20 20. /* NOTE: This is an internal header file, included by other STL headers. 21 21. * You should not attempt to use it directly. 22 22. */ 23 23. 24 24. #ifndef __STL_CONFIG_H 25 25. #define __STL_CONFIG_H 26 26. 27 27. // 本配置文件功能表: 28 28. // (1) 如果不编译器没有定义bool, true, false则定义 29 29. // (2) 如果编译器不支持drand48()函数则定义__STL_NO_DRAND48 30 30. // 注: drand48产生双精度的伪随机数, 因为采用了48bit计算, 故名drand48 31 31. // (3) 如果编译器不支持static members of template classes(模板类静态成员), 32 32. // 则定义__STL_STATIC_TEMPLATE_MEMBER_BUG 33 33. // (4) 如果编译器不支持'typename'关键字, 则将'typename'定义为空(null macro) 34 34. // (5) 如果编译器支持partial specialization of class templates(模板类偏特化), 35 35. // 则定义__STL_CLASS_PARTIAL_SPECIALIZATION 36 36. // 参考文献: http://msdn.microsoft.com/en-us/library/9w7t3kf1(v=VS.71).aspx 37 37. // (6) 如果编译器支持partial ordering of function templates(模板函数特化优先级), 38 38. // 则定义__STL_FUNCTION_TMPL_PARTIAL_ORDER 39 39. // 参考资料: http://msdn.microsoft.com/zh-cn/library/zaycz069.aspx 40 40. // (7) 如果编译器支持calling a function template by providing its template 41 41. // arguments explicitly(显式指定调用模板函数的模板参数) 42 42. // 则定义__STL_EXPLICIT_FUNCTION_TMPL_ARGS 43 43. // (8) 如果编译器支持template members of classes(类模板成员), 44 44. // 则定义__STL_MEMBER_TEMPLATES 45 45. // (9) 如果编译器不支持'explicit'关键字, 则将'explicit'定义为空(null macro) 46 46. // (10) 如果编译器不能根据前一个模板参数设定后面的默认模板参数, 47 47. // 则定义__STL_LIMITED_DEFAULT_TEMPLATES 48 48. // (11) 如果编译器处理模板函数的non-type模板参数类型推断有困难, 49 49. // 则定义__STL_NON_TYPE_TMPL_PARAM_BUG 50 50. // (12) 如果编译器不支持迭代器使用'->'操作符, 51 51. // 则定义__SGI_STL_NO_ARROW_OPERATOR 52 52. // (13) 如果编译器(在当前编译模式下)支持异常, 53 53. // 则定义__STL_USE_EXCEPTIONS 54 54. // (14) 如果我们将STL放进命名空间中, 55 55. // 则定义__STL_USE_NAMESPACES 56 56. // (15) 如果本STL在SGI的编译器上编译, 并且用户没有选择pthreads或者no threads, 57 57. // 则默认使用__STL_SGI_THREADS 58 58. // 注: POSIX thread 简称为pthread, Posix线程是一个POSIX标准线程. 59 59. // (16) 如果本STL在Win32平台的编译器上使用多线程模式编译, 60 60. // 则定义__STL_WIN32THREADS 61 61. // (17) 适当的定义命名空间相关的宏(__STD, __STL_BEGIN_NAMESPACE, 等) 62 62. // (18) 适当的定义异常相关的宏(__STL_TRY, __STL_UNWIND, 等) 63 63. // (19) 根据是否定义__STL_ASSERTIONS, 将__stl_assert定义为断言或者空(null macro) 64 64. 65 65. #ifdef _PTHREADS 66 66. # define __STL_PTHREADS 67 67. #endif 68 68. 69 69. // 如果编译器不提供本STL需要的一些功能,则定义__STL_NEED_XXX 70 70. # if defined(__sgi) && !defined(__GNUC__) 71 71. # if !defined(_BOOL) 72 72. # define __STL_NEED_BOOL 73 73. # endif 74 74. # if !defined(_TYPENAME_IS_KEYWORD) 75 75. # define __STL_NEED_TYPENAME 76 76. # endif 77 77. # ifdef _PARTIAL_SPECIALIZATION_OF_CLASS_TEMPLATES 78 78. # define __STL_CLASS_PARTIAL_SPECIALIZATION 79 79. # endif 80 80. # ifdef _MEMBER_TEMPLATES 81 81. # define __STL_MEMBER_TEMPLATES 82 82. # endif 83 83. # if !defined(_EXPLICIT_IS_KEYWORD) 84 84. # define __STL_NEED_EXPLICIT 85 85. # endif 86 86. # ifdef __EXCEPTIONS 87 87. # define __STL_USE_EXCEPTIONS 88 88. # endif 89 89. # if (_COMPILER_VERSION >= 721) && defined(_NAMESPACES) 90 90. # define __STL_USE_NAMESPACES 91 91. # endif 92 92. # if !defined(_NOTHREADS) && !defined(__STL_PTHREADS) 93 93. # define __STL_SGI_THREADS 94 94. # endif 95 95. # endif 96 96. 97 97. # ifdef __GNUC__ 98 98. # include <_G_config.h> 99 99. # if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 8) 100 100. # define __STL_STATIC_TEMPLATE_MEMBER_BUG 101 101. # define __STL_NEED_TYPENAME 102 102. # define __STL_NEED_EXPLICIT 103 103. # else 104 104. # define __STL_CLASS_PARTIAL_SPECIALIZATION 105 105. # define __STL_FUNCTION_TMPL_PARTIAL_ORDER 106 106. # define __STL_EXPLICIT_FUNCTION_TMPL_ARGS 107 107. # define __STL_MEMBER_TEMPLATES 108 108. # endif 109 109. /* glibc pre 2.0 is very buggy. We have to disable thread for it. 110 110. It should be upgraded to glibc 2.0 or later. */ 111 111. # if !defined(_NOTHREADS) && __GLIBC__ >= 2 && defined(_G_USING_THUNKS) 112 112. # define __STL_PTHREADS 113 113. # endif 114 114. # ifdef __EXCEPTIONS 115 115. # define __STL_USE_EXCEPTIONS 116 116. # endif 117 117. # endif 118 118. 119 119. // Sun C++ compiler 120 120. # if defined(__SUNPRO_CC) 121 121. # define __STL_NEED_BOOL 122 122. # define __STL_NEED_TYPENAME 123 123. # define __STL_NEED_EXPLICIT 124 124. # define __STL_USE_EXCEPTIONS 125 125. # endif 126 126. 127 127. // TODO: 这个我没找到资料, 如果你知道或者有相关资料请联系我, Thank U 128 128. # if defined(__COMO__) 129 129. # define __STL_MEMBER_TEMPLATES 130 130. # define __STL_CLASS_PARTIAL_SPECIALIZATION 131 131. # define __STL_USE_EXCEPTIONS 132 132. # define __STL_USE_NAMESPACES 133 133. # endif 134 134. 135 135. // _MSC_VER 定义微软编译器的版本 136 136. // MS VC++ 10.0 _MSC_VER = 1600 137 137. // MS VC++ 9.0 _MSC_VER = 1500 138 138. // MS VC++ 8.0 _MSC_VER = 1400 139 139. // MS VC++ 7.1 _MSC_VER = 1310 140 140. // MS VC++ 7.0 _MSC_VER = 1300 141 141. // MS VC++ 6.0 _MSC_VER = 1200 142 142. // MS VC++ 5.0 _MSC_VER = 1100 143 143. # if defined(_MSC_VER) 144 144. # if _MSC_VER > 1000 145 145. # include <yvals.h> 146 146. # else 147 147. # define __STL_NEED_BOOL 148 148. # endif 149 149. # define __STL_NO_DRAND48 150 150. # define __STL_NEED_TYPENAME 151 151. # if _MSC_VER < 1100 152 152. # define __STL_NEED_EXPLICIT 153 153. # endif 154 154. # define __STL_NON_TYPE_TMPL_PARAM_BUG 155 155. # define __SGI_STL_NO_ARROW_OPERATOR 156 156. # ifdef _CPPUNWIND 157 157. # define __STL_USE_EXCEPTIONS 158 158. # endif 159 159. # ifdef _MT 160 160. # define __STL_WIN32THREADS 161 161. # endif 162 162. # endif 163 163. 164 164. # if defined(__BORLANDC__) 165 165. # define __STL_NO_DRAND48 166 166. # define __STL_NEED_TYPENAME 167 167. # define __STL_LIMITED_DEFAULT_TEMPLATES 168 168. # define __SGI_STL_NO_ARROW_OPERATOR 169 169. # define __STL_NON_TYPE_TMPL_PARAM_BUG 170 170. # ifdef _CPPUNWIND 171 171. # define __STL_USE_EXCEPTIONS 172 172. # endif 173 173. # ifdef __MT__ 174 174. # define __STL_WIN32THREADS 175 175. # endif 176 176. # endif 177 177. 178 178. 179 179. # if defined(__STL_NEED_BOOL) 180 180. typedef int bool; 181 181. # define true 1 182 182. # define false 0 183 183. # endif 184 184. 185 185. # ifdef __STL_NEED_TYPENAME 186 186. # define typename 187 187. # endif 188 188. 189 189. # ifdef __STL_NEED_EXPLICIT 190 190. # define explicit 191 191. # endif 192 192. 193 193. # ifdef __STL_EXPLICIT_FUNCTION_TMPL_ARGS 194 194. # define __STL_NULL_TMPL_ARGS <> 195 195. # else 196 196. # define __STL_NULL_TMPL_ARGS 197 197. # endif 198 198. 199 199. # ifdef __STL_CLASS_PARTIAL_SPECIALIZATION 200 200. # define __STL_TEMPLATE_NULL template<> 201 201. # else 202 202. # define __STL_TEMPLATE_NULL 203 203. # endif 204 204. 205 205. // __STL_NO_NAMESPACES is a hook so that users can disable namespaces 206 206. // without having to edit library headers. 207 207. # if defined(__STL_USE_NAMESPACES) && !defined(__STL_NO_NAMESPACES) 208 208. # define __STD std 209 209. # define __STL_BEGIN_NAMESPACE namespace std { 210 210. # define __STL_END_NAMESPACE } 211 211. # define __STL_USE_NAMESPACE_FOR_RELOPS 212 212. # define __STL_BEGIN_RELOPS_NAMESPACE namespace std { 213 213. # define __STL_END_RELOPS_NAMESPACE } 214 214. # define __STD_RELOPS std 215 215. # else 216 216. # define __STD 217 217. # define __STL_BEGIN_NAMESPACE 218 218. # define __STL_END_NAMESPACE 219 219. # undef __STL_USE_NAMESPACE_FOR_RELOPS 220 220. # define __STL_BEGIN_RELOPS_NAMESPACE 221 221. # define __STL_END_RELOPS_NAMESPACE 222 222. # define __STD_RELOPS 223 223. # endif 224 224. 225 225. # ifdef __STL_USE_EXCEPTIONS 226 226. # define __STL_TRY try 227 227. # define __STL_CATCH_ALL catch(...) 228 228. # define __STL_RETHROW throw 229 229. # define __STL_NOTHROW throw() 230 230. # define __STL_UNWIND(action) catch(...) { action; throw; } 231 231. # else 232 232. # define __STL_TRY 233 233. # define __STL_CATCH_ALL if (false) 234 234. # define __STL_RETHROW 235 235. # define __STL_NOTHROW 236 236. # define __STL_UNWIND(action) 237 237. # endif 238 238. 239 239. #ifdef __STL_ASSERTIONS 240 240. # include <stdio.h> 241 241. # define __stl_assert(expr) \ 242 242. if (!(expr)) { fprintf(stderr, "%s:%d STL assertion failure: %s\n", \ 243 243. __FILE__, __LINE__, # expr); abort(); } 244 244. #else 245 245. # define __stl_assert(expr) 246 246. #endif 247 247. 248 248. #endif /* __STL_CONFIG_H */ 249 249. 250 250. // Local Variables: 251 251. // mode:C++ 252 252. // End:
defalloc.h
stl_alloc.h
memory.cpp
stl_construct.h
stl_uninitialized.h
stl_iterator.h
type_traits.h
stl_vector.h
stl_pair.h
stl_list.h
stl_deque.h
stl_stack.h
stl_queue.h
1 // Filename: stl_slist.h 2 3 // Comment By: 凝霜 4 // E-mail: mdl2009@vip.qq.com 5 // Blog: http://blog.csdn.net/mdl13412 6 7 /* 8 * Copyright (c) 1997 9 * Silicon Graphics Computer Systems, Inc. 10 * 11 * Permission to use, copy, modify, distribute and sell this software 12 * and its documentation for any purpose is hereby granted without fee, 13 * provided that the above copyright notice appear in all copies and 14 * that both that copyright notice and this permission notice appear 15 * in supporting documentation. Silicon Graphics makes no 16 * representations about the suitability of this software for any 17 * purpose. It is provided "as is" without express or implied warranty. 18 * 19 */ 20 21 /* NOTE: This is an internal header file, included by other STL headers. 22 * You should not attempt to use it directly. 23 */ 24 25 #ifndef __SGI_STL_INTERNAL_SLIST_H 26 #define __SGI_STL_INTERNAL_SLIST_H 27 28 29 __STL_BEGIN_NAMESPACE 30 31 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32) 32 #pragma set woff 1174 33 #endif 34 35 // 这个是链表结点的指针域 36 struct __slist_node_base 37 { 38 __slist_node_base* next; 39 }; 40 41 //// 42 // 将new_node插入到prev_node后面 43 //// 44 // 插入前 45 // 这个是prev_node 这个是new_node 46 // ↓ ↓ 47 // -------- -------- -------- -------- 48 // ... | next |--->| next |-------->| next | ... | next | 49 // -------- -------- -------- -------- 50 // 插入后 51 // 这个是prev_node 这个是new_node 52 // ↓ --------------------------------- ↓ 53 // -------- -------- | -------- | -------- 54 // ... | next |--->| next |--- -->| next | ... --->| next |--- 55 // -------- -------- | -------- -------- | 56 // ------------------------------------------- 57 //// 58 59 inline __slist_node_base* __slist_make_link(__slist_node_base* prev_node, 60 __slist_node_base* new_node) 61 { 62 new_node->next = prev_node->next; 63 prev_node->next = new_node; 64 return new_node; 65 } 66 67 // 获取指定结点的前一个结点 68 inline __slist_node_base* __slist_previous(__slist_node_base* head, 69 const __slist_node_base* node) 70 { 71 while (head && head->next != node) 72 head = head->next; 73 return head; 74 } 75 76 inline const __slist_node_base* __slist_previous(const __slist_node_base* head, 77 const __slist_node_base* node) 78 { 79 while (head && head->next != node) 80 head = head->next; 81 return head; 82 } 83 84 //// 85 // 将(first, last]链接到pos后面 86 //// 87 // 下面的例子是在同一链表进行操作的情况 88 // 操作前 89 // pos after before_first first before_last 90 // ↓ ↓ ↓ ↓ ↓ 91 // -------- -------- -------- -------- -------- -------- -------- 92 // ... | next |--->| next |--->| next |--->| next |--->| next |--->| next |--->| next | ... 93 // -------- -------- -------- -------- -------- -------- -------- 94 // 操作后 95 // pos after before_first first before_last 96 // ↓ ↓ ↓ ↓ ↓ 97 // -------- -------- -------- -------- -------- -------- -------- 98 // ... | next | ->| next |--->| next |-- | next |--->| next |--->| next | ->| next | ... 99 // -------- | -------- -------- | -------- -------- -------- | -------- 100 // | | | ↑ | | 101 // ------|----------------------|------- | | 102 // -----------------------|------------------------------- | 103 // -------------------------------------- 104 //// 105 inline void __slist_splice_after(__slist_node_base* pos, 106 __slist_node_base* before_first, 107 __slist_node_base* before_last) 108 { 109 if (pos != before_first && pos != before_last) { 110 __slist_node_base* first = before_first->next; 111 __slist_node_base* after = pos->next; 112 before_first->next = before_last->next; 113 pos->next = first; 114 before_last->next = after; 115 } 116 } 117 118 // 链表转置 119 inline __slist_node_base* __slist_reverse(__slist_node_base* node) 120 { 121 __slist_node_base* result = node; 122 node = node->next; 123 result->next = 0; 124 while(node) { 125 __slist_node_base* next = node->next; 126 node->next = result; 127 result = node; 128 node = next; 129 } 130 return result; 131 } 132 133 // 这个是真正的链表结点 134 template <class T> 135 struct __slist_node : public __slist_node_base 136 { 137 T data; 138 }; 139 140 struct __slist_iterator_base 141 { 142 typedef size_t size_type; 143 typedef ptrdiff_t difference_type; 144 typedef forward_iterator_tag iterator_category; 145 146 __slist_node_base* node; 147 148 __slist_iterator_base(__slist_node_base* x) : node(x) {} 149 void incr() { node = node->next; } 150 151 bool operator==(const __slist_iterator_base& x) const 152 { 153 return node == x.node; 154 } 155 bool operator!=(const __slist_iterator_base& x) const 156 { 157 return node != x.node; 158 } 159 }; 160 161 // 链表迭代器, 关于迭代器参考<stl_iterator.h> 162 // 由于是单向链表, 所以不能提供operator --(效率太低) 163 // 同样也不能提供随机访问能力 164 template <class T, class Ref, class Ptr> 165 struct __slist_iterator : public __slist_iterator_base 166 { 167 typedef __slist_iterator<T, T&, T*> iterator; 168 typedef __slist_iterator<T, const T&, const T*> const_iterator; 169 typedef __slist_iterator<T, Ref, Ptr> self; 170 171 typedef T value_type; 172 typedef Ptr pointer; 173 typedef Ref reference; 174 typedef __slist_node<T> list_node; 175 176 __slist_iterator(list_node* x) : __slist_iterator_base(x) {} 177 __slist_iterator() : __slist_iterator_base(0) {} 178 __slist_iterator(const iterator& x) : __slist_iterator_base(x.node) {} 179 180 reference operator*() const { return ((list_node*) node)->data; } 181 #ifndef __SGI_STL_NO_ARROW_OPERATOR 182 // 如果编译器支持'->'则重载, 详细见我在<stl_list.h>中的剖析 183 pointer operator->() const { return &(operator*()); } 184 #endif /* __SGI_STL_NO_ARROW_OPERATOR */ 185 186 self& operator++() 187 { 188 incr(); 189 return *this; 190 } 191 self operator++(int) 192 { 193 self tmp = *this; 194 incr(); 195 return tmp; 196 } 197 }; 198 199 #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION 200 201 inline ptrdiff_t* 202 distance_type(const __slist_iterator_base&) 203 { 204 return 0; 205 } 206 207 inline forward_iterator_tag 208 iterator_category(const __slist_iterator_base&) 209 { 210 return forward_iterator_tag(); 211 } 212 213 template <class T, class Ref, class Ptr> 214 inline T* 215 value_type(const __slist_iterator<T, Ref, Ptr>&) { 216 return 0; 217 } 218 219 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 220 221 // 计算链表长度, 时间复杂度O(n) 222 inline size_t __slist_size(__slist_node_base* node) 223 { 224 size_t result = 0; 225 for ( ; node != 0; node = node->next) 226 ++result; 227 return result; 228 } 229 230 template <class T, class Alloc = alloc> 231 class slist 232 { 233 public: 234 // 标记为'STL标准强制要求'的typedefs用于提供iterator_traits<I>支持 235 typedef T value_type; // STL标准强制要求 236 typedef value_type* pointer; // STL标准强制要求 237 typedef const value_type* const_pointer; 238 typedef value_type& reference; // STL标准强制要求 239 typedef const value_type& const_reference; 240 typedef size_t size_type; 241 typedef ptrdiff_t difference_type; // STL标准强制要求 242 243 typedef __slist_iterator<T, T&, T*> iterator; // STL标准强制要求 244 typedef __slist_iterator<T, const T&, const T*> const_iterator; 245 246 private: 247 typedef __slist_node<T> list_node; 248 typedef __slist_node_base list_node_base; 249 typedef __slist_iterator_base iterator_base; 250 251 // 这个提供STL标准的allocator接口 252 typedef simple_alloc<list_node, Alloc> list_node_allocator; 253 254 // 创建一个值为x的结点, 其没有后继结点 255 static list_node* create_node(const value_type& x) 256 { 257 list_node* node = list_node_allocator::allocate(); 258 __STL_TRY { 259 construct(&node->data, x); 260 node->next = 0; 261 } 262 __STL_UNWIND(list_node_allocator::deallocate(node)); 263 return node; 264 } 265 266 // 析构一个结点的数据, 不释放内存 267 static void destroy_node(list_node* node) 268 { 269 destroy(&node->data); 270 list_node_allocator::deallocate(node); 271 } 272 273 //// 274 // 在头结点插入n个值为x的结点 275 //// 276 // fill_initialize(size_type n, const value_type& x) 277 // ↓ 278 // _insert_after_fill(&head, n, x); 279 // ↓ 280 // for (size_type i = 0; i < n; ++i) 281 // pos = __slist_make_link(pos, create_node(x)); 282 // | 283 // | 284 // ↓ 285 // create_node(const value_type& x) 286 // list_node_allocator::allocate(); 287 // construct(&node->data, x); 288 //// 289 void fill_initialize(size_type n, const value_type& x) 290 { 291 head.next = 0; 292 __STL_TRY { 293 _insert_after_fill(&head, n, x); 294 } 295 __STL_UNWIND(clear()); 296 } 297 298 // 在头结点后面插入[first, last)区间内的结点, 注意是新建立结点 299 #ifdef __STL_MEMBER_TEMPLATES 300 template <class InputIterator> 301 void range_initialize(InputIterator first, InputIterator last) 302 { 303 head.next = 0; 304 __STL_TRY { 305 _insert_after_range(&head, first, last); 306 } 307 __STL_UNWIND(clear()); 308 } 309 #else /* __STL_MEMBER_TEMPLATES */ 310 void range_initialize(const value_type* first, const value_type* last) { 311 head.next = 0; 312 __STL_TRY { 313 _insert_after_range(&head, first, last); 314 } 315 __STL_UNWIND(clear()); 316 } 317 void range_initialize(const_iterator first, const_iterator last) { 318 head.next = 0; 319 __STL_TRY { 320 _insert_after_range(&head, first, last); 321 } 322 __STL_UNWIND(clear()); 323 } 324 #endif /* __STL_MEMBER_TEMPLATES */ 325 326 private: 327 list_node_base head; // 这是链表头 328 329 public: 330 slist() { head.next = 0; } 331 332 slist(size_type n, const value_type& x) { fill_initialize(n, x); } 333 slist(int n, const value_type& x) { fill_initialize(n, x); } 334 slist(long n, const value_type& x) { fill_initialize(n, x); } 335 explicit slist(size_type n) { fill_initialize(n, value_type()); } 336 337 #ifdef __STL_MEMBER_TEMPLATES 338 template <class InputIterator> 339 slist(InputIterator first, InputIterator last) 340 { 341 range_initialize(first, last); 342 } 343 344 #else /* __STL_MEMBER_TEMPLATES */ 345 slist(const_iterator first, const_iterator last) { 346 range_initialize(first, last); 347 } 348 slist(const value_type* first, const value_type* last) { 349 range_initialize(first, last); 350 } 351 #endif /* __STL_MEMBER_TEMPLATES */ 352 353 slist(const slist& L) { range_initialize(L.begin(), L.end()); } 354 355 slist& operator= (const slist& L); 356 357 // 析构所有元素, 并释放内存 358 ~slist() { clear(); } 359 360 public: 361 362 iterator begin() { return iterator((list_node*)head.next); } 363 const_iterator begin() const { return const_iterator((list_node*)head.next);} 364 365 iterator end() { return iterator(0); } 366 const_iterator end() const { return const_iterator(0); } 367 368 size_type size() const { return __slist_size(head.next); } 369 370 size_type max_size() const { return size_type(-1); } 371 372 bool empty() const { return head.next == 0; } 373 374 // 只需交换链表头数据就能实现交换^_^ 375 void swap(slist& L) 376 { 377 list_node_base* tmp = head.next; 378 head.next = L.head.next; 379 L.head.next = tmp; 380 } 381 382 public: 383 friend bool operator== __STL_NULL_TMPL_ARGS(const slist<T, Alloc>& L1, 384 const slist<T, Alloc>& L2); 385 386 public: 387 388 // OK. 下面四个函数时间复杂度为O(1) 389 // 对于插入操作只推荐push_front()其余操作个人感觉很慢 390 reference front() { return ((list_node*) head.next)->data; } 391 const_reference front() const { return ((list_node*) head.next)->data; } 392 void push_front(const value_type& x) 393 { 394 __slist_make_link(&head, create_node(x)); 395 } 396 void pop_front() 397 { 398 list_node* node = (list_node*) head.next; 399 head.next = node->next; 400 destroy_node(node); 401 } 402 403 // 获取指定结点的前驱结点 404 iterator previous(const_iterator pos) 405 { 406 return iterator((list_node*) __slist_previous(&head, pos.node)); 407 } 408 const_iterator previous(const_iterator pos) const 409 { 410 return const_iterator((list_node*) __slist_previous(&head, pos.node)); 411 } 412 413 private: 414 // 在指定结点后插入值为x的元素, 分配内存 415 list_node* _insert_after(list_node_base* pos, const value_type& x) 416 { 417 return (list_node*) (__slist_make_link(pos, create_node(x))); 418 } 419 420 // 在指定结点后面插入n个值为x的元素 421 void _insert_after_fill(list_node_base* pos, 422 size_type n, const value_type& x) 423 { 424 for (size_type i = 0; i < n; ++i) 425 pos = __slist_make_link(pos, create_node(x)); 426 } 427 428 // TODO: 待分析 429 // 在pos后面插入[first, last)区间内的元素 430 #ifdef __STL_MEMBER_TEMPLATES 431 template <class InIter> 432 void _insert_after_range(list_node_base* pos, InIter first, InIter last) 433 { 434 while (first != last) { 435 pos = __slist_make_link(pos, create_node(*first)); 436 ++first; 437 } 438 } 439 #else /* __STL_MEMBER_TEMPLATES */ 440 void _insert_after_range(list_node_base* pos, 441 const_iterator first, const_iterator last) { 442 while (first != last) { 443 pos = __slist_make_link(pos, create_node(*first)); 444 ++first; 445 } 446 } 447 void _insert_after_range(list_node_base* pos, 448 const value_type* first, const value_type* last) { 449 while (first != last) { 450 pos = __slist_make_link(pos, create_node(*first)); 451 ++first; 452 } 453 } 454 #endif /* __STL_MEMBER_TEMPLATES */ 455 456 // 擦除pos后面的结点 457 list_node_base* erase_after(list_node_base* pos) 458 { 459 list_node* next = (list_node*) (pos->next); 460 list_node_base* next_next = next->next; 461 pos->next = next_next; 462 destroy_node(next); 463 return next_next; 464 } 465 466 // 擦除(before_first, last_node)区间的结点 467 list_node_base* erase_after(list_node_base* before_first, 468 list_node_base* last_node) 469 { 470 list_node* cur = (list_node*) (before_first->next); 471 while (cur != last_node) { 472 list_node* tmp = cur; 473 cur = (list_node*) cur->next; 474 destroy_node(tmp); 475 } 476 before_first->next = last_node; 477 return last_node; 478 } 479 480 public: 481 // 在pos后面插入值为x的结点 482 iterator insert_after(iterator pos, const value_type& x) 483 { 484 return iterator(_insert_after(pos.node, x)); 485 } 486 487 iterator insert_after(iterator pos) 488 { 489 return insert_after(pos, value_type()); 490 } 491 492 void insert_after(iterator pos, size_type n, const value_type& x) 493 { 494 _insert_after_fill(pos.node, n, x); 495 } 496 void insert_after(iterator pos, int n, const value_type& x) 497 { 498 _insert_after_fill(pos.node, (size_type) n, x); 499 } 500 void insert_after(iterator pos, long n, const value_type& x) 501 { 502 _insert_after_fill(pos.node, (size_type) n, x); 503 } 504 505 #ifdef __STL_MEMBER_TEMPLATES 506 template <class InIter> 507 void insert_after(iterator pos, InIter first, InIter last) { 508 _insert_after_range(pos.node, first, last); 509 } 510 #else /* __STL_MEMBER_TEMPLATES */ 511 void insert_after(iterator pos, const_iterator first, const_iterator last) { 512 _insert_after_range(pos.node, first, last); 513 } 514 void insert_after(iterator pos, 515 const value_type* first, const value_type* last) { 516 _insert_after_range(pos.node, first, last); 517 } 518 #endif /* __STL_MEMBER_TEMPLATES */ 519 520 // 在pos后面插入值为x的结点 521 iterator insert(iterator pos, const value_type& x) 522 { 523 return iterator(_insert_after(__slist_previous(&head, pos.node), x)); 524 } 525 526 iterator insert(iterator pos) 527 { 528 return iterator(_insert_after(__slist_previous(&head, pos.node), 529 value_type())); 530 } 531 532 // 在pos前插入m个值为x的结点 533 void insert(iterator pos, size_type n, const value_type& x) 534 { 535 _insert_after_fill(__slist_previous(&head, pos.node), n, x); 536 } 537 void insert(iterator pos, int n, const value_type& x) 538 { 539 _insert_after_fill(__slist_previous(&head, pos.node), (size_type) n, x); 540 } 541 void insert(iterator pos, long n, const value_type& x) 542 { 543 _insert_after_fill(__slist_previous(&head, pos.node), (size_type) n, x); 544 } 545 546 #ifdef __STL_MEMBER_TEMPLATES 547 template <class InIter> 548 void insert(iterator pos, InIter first, InIter last) { 549 _insert_after_range(__slist_previous(&head, pos.node), first, last); 550 } 551 #else /* __STL_MEMBER_TEMPLATES */ 552 void insert(iterator pos, const_iterator first, const_iterator last) { 553 _insert_after_range(__slist_previous(&head, pos.node), first, last); 554 } 555 void insert(iterator pos, const value_type* first, const value_type* last) { 556 _insert_after_range(__slist_previous(&head, pos.node), first, last); 557 } 558 #endif /* __STL_MEMBER_TEMPLATES */ 559 560 public: 561 iterator erase_after(iterator pos) 562 { 563 return iterator((list_node*)erase_after(pos.node)); 564 } 565 iterator erase_after(iterator before_first, iterator last) 566 { 567 return iterator((list_node*)erase_after(before_first.node, last.node)); 568 } 569 570 iterator erase(iterator pos) 571 { 572 return (list_node*) erase_after(__slist_previous(&head, pos.node)); 573 } 574 iterator erase(iterator first, iterator last) 575 { 576 return (list_node*) erase_after(__slist_previous(&head, first.node), 577 last.node); 578 } 579 580 // 详细剖析见后面实现部分 581 void resize(size_type new_size, const T& x); 582 void resize(size_type new_size) { resize(new_size, T()); } 583 void clear() { erase_after(&head, 0); } 584 585 public: 586 // splic操作可以参考<stl_list.h>的说明 587 588 // Moves the range [before_first + 1, before_last + 1) to *this, 589 // inserting it immediately after pos. This is constant time. 590 void splice_after(iterator pos, 591 iterator before_first, iterator before_last) 592 { 593 if (before_first != before_last) 594 __slist_splice_after(pos.node, before_first.node, before_last.node); 595 } 596 597 // Moves the element that follows prev to *this, inserting it immediately 598 // after pos. This is constant time. 599 600 void splice_after(iterator pos, iterator prev) 601 { 602 __slist_splice_after(pos.node, prev.node, prev.node->next); 603 } 604 605 // Linear in distance(begin(), pos), and linear in L.size(). 606 void splice(iterator pos, slist& L) 607 { 608 if (L.head.next) 609 __slist_splice_after(__slist_previous(&head, pos.node), 610 &L.head, 611 __slist_previous(&L.head, 0)); 612 } 613 614 // Linear in distance(begin(), pos), and in distance(L.begin(), i). 615 void splice(iterator pos, slist& L, iterator i) 616 { 617 __slist_splice_after(__slist_previous(&head, pos.node), 618 __slist_previous(&L.head, i.node), 619 i.node); 620 } 621 622 // Linear in distance(begin(), pos), in distance(L.begin(), first), 623 // and in distance(first, last). 624 void splice(iterator pos, slist& L, iterator first, iterator last) 625 { 626 if (first != last) 627 __slist_splice_after(__slist_previous(&head, pos.node), 628 __slist_previous(&L.head, first.node), 629 __slist_previous(first.node, last.node)); 630 } 631 632 public: 633 // 这些接口可以参考<stl_list.h> 634 void reverse() { if (head.next) head.next = __slist_reverse(head.next); } 635 636 void remove(const T& val); 637 void unique(); 638 void merge(slist& L); 639 void sort(); 640 641 #ifdef __STL_MEMBER_TEMPLATES 642 template <class Predicate> void remove_if(Predicate pred); 643 template <class BinaryPredicate> void unique(BinaryPredicate pred); 644 template <class StrictWeakOrdering> void merge(slist&, StrictWeakOrdering); 645 template <class StrictWeakOrdering> void sort(StrictWeakOrdering comp); 646 #endif /* __STL_MEMBER_TEMPLATES */ 647 }; 648 649 // 实现整个链表的赋值, 会析构原有的元素 650 template <class T, class Alloc> 651 slist<T, Alloc>& slist<T,Alloc>::operator=(const slist<T, Alloc>& L) 652 { 653 if (&L != this) { 654 list_node_base* p1 = &head; 655 list_node* n1 = (list_node*) head.next; 656 const list_node* n2 = (const list_node*) L.head.next; 657 while (n1 && n2) { 658 n1->data = n2->data; 659 p1 = n1; 660 n1 = (list_node*) n1->next; 661 n2 = (const list_node*) n2->next; 662 } 663 if (n2 == 0) 664 erase_after(p1, 0); 665 else 666 _insert_after_range(p1, 667 const_iterator((list_node*)n2), const_iterator(0)); 668 } 669 return *this; 670 } 671 672 // 只有两个链表所有内容都相等才判定其等价 673 // 不过个人觉得只需要判断头结点指向的第一个结点就可以 674 // 大家可以讨论一下 675 template <class T, class Alloc> 676 bool operator==(const slist<T, Alloc>& L1, const slist<T, Alloc>& L2) 677 { 678 typedef typename slist<T,Alloc>::list_node list_node; 679 list_node* n1 = (list_node*) L1.head.next; 680 list_node* n2 = (list_node*) L2.head.next; 681 while (n1 && n2 && n1->data == n2->data) { 682 n1 = (list_node*) n1->next; 683 n2 = (list_node*) n2->next; 684 } 685 return n1 == 0 && n2 == 0; 686 } 687 688 // 字典序比较 689 template <class T, class Alloc> 690 inline bool operator<(const slist<T, Alloc>& L1, const slist<T, Alloc>& L2) 691 { 692 return lexicographical_compare(L1.begin(), L1.end(), L2.begin(), L2.end()); 693 } 694 695 // 如果编译器支持模板函数特化优先级 696 // 那么将全局的swap实现为使用slist私有的swap以提高效率 697 #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER 698 699 template <class T, class Alloc> 700 inline void swap(slist<T, Alloc>& x, slist<T, Alloc>& y) { 701 x.swap(y); 702 } 703 704 #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */ 705 706 //// 707 // 下面这些接口和list的行为一致, 只是算法有些不同, 请参考<stl_list.h> 708 //// 709 710 template <class T, class Alloc> 711 void slist<T, Alloc>::resize(size_type len, const T& x) 712 { 713 list_node_base* cur = &head; 714 while (cur->next != 0 && len > 0) { 715 --len; 716 cur = cur->next; 717 } 718 if (cur->next) 719 erase_after(cur, 0); 720 else 721 _insert_after_fill(cur, len, x); 722 } 723 724 template <class T, class Alloc> 725 void slist<T,Alloc>::remove(const T& val) 726 { 727 list_node_base* cur = &head; 728 while (cur && cur->next) { 729 if (((list_node*) cur->next)->data == val) 730 erase_after(cur); 731 else 732 cur = cur->next; 733 } 734 } 735 736 template <class T, class Alloc> 737 void slist<T,Alloc>::unique() 738 { 739 list_node_base* cur = head.next; 740 if (cur) { 741 while (cur->next) { 742 if (((list_node*)cur)->data == ((list_node*)(cur->next))->data) 743 erase_after(cur); 744 else 745 cur = cur->next; 746 } 747 } 748 } 749 750 template <class T, class Alloc> 751 void slist<T,Alloc>::merge(slist<T,Alloc>& L) 752 { 753 list_node_base* n1 = &head; 754 while (n1->next && L.head.next) { 755 if (((list_node*) L.head.next)->data < ((list_node*) n1->next)->data) 756 __slist_splice_after(n1, &L.head, L.head.next); 757 n1 = n1->next; 758 } 759 if (L.head.next) { 760 n1->next = L.head.next; 761 L.head.next = 0; 762 } 763 } 764 765 template <class T, class Alloc> 766 void slist<T,Alloc>::sort() 767 { 768 if (head.next && head.next->next) { 769 slist carry; 770 slist counter[64]; 771 int fill = 0; 772 while (!empty()) { 773 __slist_splice_after(&carry.head, &head, head.next); 774 int i = 0; 775 while (i < fill && !counter[i].empty()) { 776 counter[i].merge(carry); 777 carry.swap(counter[i]); 778 ++i; 779 } 780 carry.swap(counter[i]); 781 if (i == fill) 782 ++fill; 783 } 784 785 for (int i = 1; i < fill; ++i) 786 counter[i].merge(counter[i-1]); 787 this->swap(counter[fill-1]); 788 } 789 } 790 791 #ifdef __STL_MEMBER_TEMPLATES 792 793 template <class T, class Alloc> 794 template <class Predicate> void slist<T,Alloc>::remove_if(Predicate pred) 795 { 796 list_node_base* cur = &head; 797 while (cur->next) { 798 if (pred(((list_node*) cur->next)->data)) 799 erase_after(cur); 800 else 801 cur = cur->next; 802 } 803 } 804 805 template <class T, class Alloc> template <class BinaryPredicate> 806 void slist<T,Alloc>::unique(BinaryPredicate pred) 807 { 808 list_node* cur = (list_node*) head.next; 809 if (cur) { 810 while (cur->next) { 811 if (pred(((list_node*)cur)->data, ((list_node*)(cur->next))->data)) 812 erase_after(cur); 813 else 814 cur = (list_node*) cur->next; 815 } 816 } 817 } 818 819 template <class T, class Alloc> template <class StrictWeakOrdering> 820 void slist<T,Alloc>::merge(slist<T,Alloc>& L, StrictWeakOrdering comp) 821 { 822 list_node_base* n1 = &head; 823 while (n1->next && L.head.next) { 824 if (comp(((list_node*) L.head.next)->data, 825 ((list_node*) n1->next)->data)) 826 __slist_splice_after(n1, &L.head, L.head.next); 827 n1 = n1->next; 828 } 829 if (L.head.next) { 830 n1->next = L.head.next; 831 L.head.next = 0; 832 } 833 } 834 835 template <class T, class Alloc> template <class StrictWeakOrdering> 836 void slist<T,Alloc>::sort(StrictWeakOrdering comp) 837 { 838 if (head.next && head.next->next) { 839 slist carry; 840 slist counter[64]; 841 int fill = 0; 842 while (!empty()) { 843 __slist_splice_after(&carry.head, &head, head.next); 844 int i = 0; 845 while (i < fill && !counter[i].empty()) { 846 counter[i].merge(carry, comp); 847 carry.swap(counter[i]); 848 ++i; 849 } 850 carry.swap(counter[i]); 851 if (i == fill) 852 ++fill; 853 } 854 855 for (int i = 1; i < fill; ++i) 856 counter[i].merge(counter[i-1], comp); 857 this->swap(counter[fill-1]); 858 } 859 } 860 861 #endif /* __STL_MEMBER_TEMPLATES */ 862 863 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32) 864 #pragma reset woff 1174 865 #endif 866 867 __STL_END_NAMESPACE 868 869 #endif /* __SGI_STL_INTERNAL_SLIST_H */ 870 871 // Local Variables: 872 // mode:C++ 873 // End:
stl_heap.h
stl_tree.h
stl_set.h
stl_multiset.h
stl_map.h
stl_multimap.h
stl_hashtable.h
stl_hash_set.h
stl_hash_map.h
stl_algobase.h
stl_relops.h
1 // Filename: <stl_algo.h> 2 3 // Comment By: 凝霜 4 // E-mail: mdl2009@vip.qq.com 5 // Blog: http://blog.csdn.net/mdl13412 6 7 // 这个文件中定义了一些STL关键的算法, 我仅仅给出一个思路, 8 // 不进行详尽讲解, 具体算法请参考算法书籍, 推荐《算法导论》 9 // 另外, 对于基础薄弱的, 推荐《大话数据结构》, 此书我读了一下 10 // 试读章节, 适合初学者学习 11 12 /* 13 * 14 * Copyright (c) 1994 15 * Hewlett-Packard Company 16 * 17 * Permission to use, copy, modify, distribute and sell this software 18 * and its documentation for any purpose is hereby granted without fee, 19 * provided that the above copyright notice appear in all copies and 20 * that both that copyright notice and this permission notice appear 21 * in supporting documentation. Hewlett-Packard Company makes no 22 * representations about the suitability of this software for any 23 * purpose. It is provided "as is" without express or implied warranty. 24 * 25 * 26 * Copyright (c) 1996 27 * Silicon Graphics Computer Systems, Inc. 28 * 29 * Permission to use, copy, modify, distribute and sell this software 30 * and its documentation for any purpose is hereby granted without fee, 31 * provided that the above copyright notice appear in all copies and 32 * that both that copyright notice and this permission notice appear 33 * in supporting documentation. Silicon Graphics makes no 34 * representations about the suitability of this software for any 35 * purpose. It is provided "as is" without express or implied warranty. 36 */ 37 38 /* NOTE: This is an internal header file, included by other STL headers. 39 * You should not attempt to use it directly. 40 */ 41 42 #ifndef __SGI_STL_INTERNAL_ALGO_H 43 #define __SGI_STL_INTERNAL_ALGO_H 44 45 #include <stl_heap.h> 46 47 __STL_BEGIN_NAMESPACE 48 49 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32) 50 #pragma set woff 1209 51 #endif 52 53 // 选取a, b, c三个数中间的那个 54 template <class T> 55 inline const T& __median(const T& a, const T& b, const T& c) { 56 if (a < b) 57 if (b < c) 58 return b; 59 else if (a < c) 60 return c; 61 else 62 return a; 63 else if (a < c) 64 return a; 65 else if (b < c) 66 return c; 67 else 68 return b; 69 } 70 71 template <class T, class Compare> 72 inline const T& __median(const T& a, const T& b, const T& c, Compare comp) { 73 if (comp(a, b)) 74 if (comp(b, c)) 75 return b; 76 else if (comp(a, c)) 77 return c; 78 else 79 return a; 80 else if (comp(a, c)) 81 return a; 82 else if (comp(b, c)) 83 return c; 84 else 85 return b; 86 } 87 88 // 对于[first, last)区间内的元素调用判别式 89 // 个人非常喜欢这个函数, 在C#中这个是语言层面就支持的 90 template <class InputIterator, class Function> 91 Function for_each(InputIterator first, InputIterator last, Function f) { 92 for ( ; first != last; ++first) 93 f(*first); 94 return f; 95 } 96 97 // 查找指定区间内第一个值为value的元素 98 template <class InputIterator, class T> 99 InputIterator find(InputIterator first, InputIterator last, const T& value) 100 { 101 while (first != last && *first != value) ++first; 102 return first; 103 } 104 105 // 查找指定区间内第一个满足判别式额元素 106 template <class InputIterator, class Predicate> 107 InputIterator find_if(InputIterator first, InputIterator last, 108 Predicate pred) 109 { 110 while (first != last && !pred(*first)) ++first; 111 return first; 112 } 113 114 // 找出第一组满足条件的相邻元素 115 template <class ForwardIterator> 116 ForwardIterator adjacent_find(ForwardIterator first, ForwardIterator last) 117 { 118 if (first == last) return last; 119 ForwardIterator next = first; 120 while(++next != last) { 121 // 判断是否满足条件, 满足就返回 122 if (*first == *next) return first; 123 first = next; 124 } 125 return last; 126 } 127 128 // 使用用户指定的二元比较判别式, 其余同上面 129 template <class ForwardIterator, class BinaryPredicate> 130 ForwardIterator adjacent_find(ForwardIterator first, ForwardIterator last, 131 BinaryPredicate binary_pred) 132 { 133 if (first == last) return last; 134 ForwardIterator next = first; 135 while(++next != last) { 136 if (binary_pred(*first, *next)) return first; 137 first = next; 138 } 139 return last; 140 } 141 142 // 统计指定元素在指定区间内出现的次数 143 template <class InputIterator, class T, class Size> 144 void count(InputIterator first, InputIterator last, const T& value, 145 Size& n) 146 { 147 // 统计操作要历遍整个区间 148 for ( ; first != last; ++first) 149 if (*first == value) 150 ++n; 151 } 152 153 // 统计满足指定判别式的元素的个数 154 template <class InputIterator, class Predicate, class Size> 155 void count_if(InputIterator first, InputIterator last, Predicate pred, 156 Size& n) { 157 for ( ; first != last; ++first) 158 if (pred(*first)) 159 ++n; 160 } 161 162 #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION 163 164 template <class InputIterator, class T> 165 typename iterator_traits<InputIterator>::difference_type 166 count(InputIterator first, InputIterator last, const T& value) 167 { 168 typename iterator_traits<InputIterator>::difference_type n = 0; 169 for ( ; first != last; ++first) 170 if (*first == value) 171 ++n; 172 return n; 173 } 174 175 template <class InputIterator, class Predicate> 176 typename iterator_traits<InputIterator>::difference_type 177 count_if(InputIterator first, InputIterator last, Predicate pred) { 178 typename iterator_traits<InputIterator>::difference_type n = 0; 179 for ( ; first != last; ++first) 180 if (pred(*first)) 181 ++n; 182 return n; 183 } 184 185 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 186 187 template <class ForwardIterator1, class ForwardIterator2, class Distance1, 188 class Distance2> 189 ForwardIterator1 __search(ForwardIterator1 first1, ForwardIterator1 last1, 190 ForwardIterator2 first2, ForwardIterator2 last2, 191 Distance1*, Distance2*) { 192 Distance1 d1 = 0; 193 distance(first1, last1, d1); 194 Distance2 d2 = 0; 195 distance(first2, last2, d2); 196 197 if (d1 < d2) return last1; 198 199 ForwardIterator1 current1 = first1; 200 ForwardIterator2 current2 = first2; 201 202 while (current2 != last2) 203 if (*current1 == *current2) { 204 ++current1; 205 ++current2; 206 } 207 else { 208 if (d1 == d2) 209 return last1; 210 else { 211 current1 = ++first1; 212 current2 = first2; 213 --d1; 214 } 215 } 216 return first1; 217 } 218 219 // 在[first1, last1)区间内, 查找[first2, last2)区间 220 // 为了效率, 进行函数派发 221 template <class ForwardIterator1, class ForwardIterator2> 222 inline ForwardIterator1 search(ForwardIterator1 first1, ForwardIterator1 last1, 223 ForwardIterator2 first2, ForwardIterator2 last2) 224 { 225 return __search(first1, last1, first2, last2, distance_type(first1), 226 distance_type(first2)); 227 } 228 229 template <class ForwardIterator1, class ForwardIterator2, 230 class BinaryPredicate, class Distance1, class Distance2> 231 ForwardIterator1 __search(ForwardIterator1 first1, ForwardIterator1 last1, 232 ForwardIterator2 first2, ForwardIterator2 last2, 233 BinaryPredicate binary_pred, Distance1*, Distance2*) { 234 Distance1 d1 = 0; 235 distance(first1, last1, d1); 236 Distance2 d2 = 0; 237 distance(first2, last2, d2); 238 239 if (d1 < d2) return last1; 240 241 ForwardIterator1 current1 = first1; 242 ForwardIterator2 current2 = first2; 243 244 while (current2 != last2) 245 if (binary_pred(*current1, *current2)) { 246 ++current1; 247 ++current2; 248 } 249 else { 250 if (d1 == d2) 251 return last1; 252 else { 253 current1 = ++first1; 254 current2 = first2; 255 --d1; 256 } 257 } 258 return first1; 259 } 260 261 template <class ForwardIterator1, class ForwardIterator2, 262 class BinaryPredicate> 263 inline ForwardIterator1 search(ForwardIterator1 first1, ForwardIterator1 last1, 264 ForwardIterator2 first2, ForwardIterator2 last2, 265 BinaryPredicate binary_pred) { 266 return __search(first1, last1, first2, last2, binary_pred, 267 distance_type(first1), distance_type(first2)); 268 } 269 270 // 在[first, last)内查找第一个满足连续count个value的位置 271 template <class ForwardIterator, class Integer, class T> 272 ForwardIterator search_n(ForwardIterator first, ForwardIterator last, 273 Integer count, const T& value) 274 { 275 if (count <= 0) 276 return first; 277 else { 278 first = find(first, last, value); 279 while (first != last) { 280 Integer n = count - 1; 281 ForwardIterator i = first; 282 ++i; 283 while (i != last && n != 0 && *i == value) { 284 ++i; 285 --n; 286 } 287 if (n == 0) 288 return first; 289 else 290 first = find(i, last, value); 291 } 292 return last; 293 } 294 } 295 296 // 好吧, 二元判别式自己指定的 297 template <class ForwardIterator, class Integer, class T, class BinaryPredicate> 298 ForwardIterator search_n(ForwardIterator first, ForwardIterator last, 299 Integer count, const T& value, 300 BinaryPredicate binary_pred) { 301 if (count <= 0) 302 return first; 303 else { 304 while (first != last) { 305 if (binary_pred(*first, value)) break; 306 ++first; 307 } 308 while (first != last) { 309 Integer n = count - 1; 310 ForwardIterator i = first; 311 ++i; 312 while (i != last && n != 0 && binary_pred(*i, value)) { 313 ++i; 314 --n; 315 } 316 if (n == 0) 317 return first; 318 else { 319 while (i != last) { 320 if (binary_pred(*i, value)) break; 321 ++i; 322 } 323 first = i; 324 } 325 } 326 return last; 327 } 328 } 329 330 // 交换两个区间内的元素, 要求长度相同 331 template <class ForwardIterator1, class ForwardIterator2> 332 ForwardIterator2 swap_ranges(ForwardIterator1 first1, ForwardIterator1 last1, 333 ForwardIterator2 first2) 334 { 335 for ( ; first1 != last1; ++first1, ++first2) 336 iter_swap(first1, first2); 337 return first2; 338 } 339 340 // 将[first, last)经判别式转换到result处 341 template <class InputIterator, class OutputIterator, class UnaryOperation> 342 OutputIterator transform(InputIterator first, InputIterator last, 343 OutputIterator result, UnaryOperation op) 344 { 345 for ( ; first != last; ++first, ++result) 346 *result = op(*first); 347 return result; 348 } 349 350 // 这个多了一个区间 351 template <class InputIterator1, class InputIterator2, class OutputIterator, 352 class BinaryOperation> 353 OutputIterator transform(InputIterator1 first1, InputIterator1 last1, 354 InputIterator2 first2, OutputIterator result, 355 BinaryOperation binary_op) 356 { 357 for ( ; first1 != last1; ++first1, ++first2, ++result) 358 *result = binary_op(*first1, *first2); 359 return result; 360 } 361 362 // 将[first, last)内的old_value都以new_value替代 363 template <class ForwardIterator, class T> 364 void replace(ForwardIterator first, ForwardIterator last, const T& old_value, 365 const T& new_value) 366 { 367 for ( ; first != last; ++first) 368 if (*first == old_value) *first = new_value; 369 } 370 371 // 将[first, last)内的满足判别式的元素都以new_value代替 372 template <class ForwardIterator, class Predicate, class T> 373 void replace_if(ForwardIterator first, ForwardIterator last, Predicate pred, 374 const T& new_value) 375 { 376 for ( ; first != last; ++first) 377 if (pred(*first)) *first = new_value; 378 } 379 380 // 与replace唯一不同的是会将元素复制到新的位置 381 template <class InputIterator, class OutputIterator, class T> 382 OutputIterator replace_copy(InputIterator first, InputIterator last, 383 OutputIterator result, const T& old_value, 384 const T& new_value) 385 { 386 for ( ; first != last; ++first, ++result) 387 *result = *first == old_value ? new_value : *first; 388 return result; 389 } 390 391 // 同上 392 template <class Iterator, class OutputIterator, class Predicate, class T> 393 OutputIterator replace_copy_if(Iterator first, Iterator last, 394 OutputIterator result, Predicate pred, 395 const T& new_value) 396 { 397 for ( ; first != last; ++first, ++result) 398 *result = pred(*first) ? new_value : *first; 399 return result; 400 } 401 402 // 将仿函数的处理结果填充在[first, last)区间内 403 // 对于用户自定义类型要提供operator =() 404 template <class ForwardIterator, class Generator> 405 void generate(ForwardIterator first, ForwardIterator last, Generator gen) 406 { 407 for ( ; first != last; ++first) 408 *first = gen(); 409 } 410 411 // 和generate()差不多, 只是给定的是起点和个数 412 template <class OutputIterator, class Size, class Generator> 413 OutputIterator generate_n(OutputIterator first, Size n, Generator gen) 414 { 415 for ( ; n > 0; --n, ++first) 416 *first = gen(); 417 return first; 418 } 419 420 // 将[first, last)中除了value的元素拷贝到result处 421 // 注意: 这里使用的是operator =(), 用户自定义类型要注意资源的析构 422 template <class InputIterator, class OutputIterator, class T> 423 OutputIterator remove_copy(InputIterator first, InputIterator last, 424 OutputIterator result, const T& value) 425 { 426 for ( ; first != last; ++first) 427 if (*first != value) { 428 *result = *first; 429 ++result; 430 } 431 return result; 432 } 433 434 // 将[first, last)中除了满足判别式的元素拷贝到result处 435 // 注意: 这里使用的是operator =(), 用户自定义类型要注意资源的析构 436 template <class InputIterator, class OutputIterator, class Predicate> 437 OutputIterator remove_copy_if(InputIterator first, InputIterator last, 438 OutputIterator result, Predicate pred) 439 { 440 for ( ; first != last; ++first) 441 if (!pred(*first)) { 442 *result = *first; 443 ++result; 444 } 445 return result; 446 } 447 448 // 移除指定值的元素, 但是并不删除 449 template <class ForwardIterator, class T> 450 ForwardIterator remove(ForwardIterator first, ForwardIterator last, 451 const T& value) 452 { 453 first = find(first, last, value); 454 ForwardIterator next = first; 455 return first == last ? first : remove_copy(++next, last, first, value); 456 } 457 458 // 移除满足判别式的元素, 但是并不删除 459 template <class ForwardIterator, class Predicate> 460 ForwardIterator remove_if(ForwardIterator first, ForwardIterator last, 461 Predicate pred) 462 { 463 first = find_if(first, last, pred); 464 ForwardIterator next = first; 465 return first == last ? first : remove_copy_if(++next, last, first, pred); 466 } 467 468 template <class InputIterator, class ForwardIterator> 469 ForwardIterator __unique_copy(InputIterator first, InputIterator last, 470 ForwardIterator result, forward_iterator_tag) { 471 *result = *first; 472 while (++first != last) 473 if (*result != *first) *++result = *first; 474 return ++result; 475 } 476 477 478 template <class InputIterator, class OutputIterator, class T> 479 OutputIterator __unique_copy(InputIterator first, InputIterator last, 480 OutputIterator result, T*) { 481 T value = *first; 482 *result = value; 483 while (++first != last) 484 if (value != *first) { 485 value = *first; 486 *++result = value; 487 } 488 return ++result; 489 } 490 491 template <class InputIterator, class OutputIterator> 492 inline OutputIterator __unique_copy(InputIterator first, InputIterator last, 493 OutputIterator result, 494 output_iterator_tag) { 495 return __unique_copy(first, last, result, value_type(first)); 496 } 497 498 template <class InputIterator, class OutputIterator> 499 inline OutputIterator unique_copy(InputIterator first, InputIterator last, 500 OutputIterator result) { 501 if (first == last) return result; 502 return __unique_copy(first, last, result, iterator_category(result)); 503 } 504 template <class InputIterator, class ForwardIterator, class BinaryPredicate> 505 ForwardIterator __unique_copy(InputIterator first, InputIterator last, 506 ForwardIterator result, 507 BinaryPredicate binary_pred, 508 forward_iterator_tag) { 509 *result = *first; 510 while (++first != last) 511 if (!binary_pred(*result, *first)) *++result = *first; 512 return ++result; 513 } 514 515 template <class InputIterator, class OutputIterator, class BinaryPredicate, 516 class T> 517 OutputIterator __unique_copy(InputIterator first, InputIterator last, 518 OutputIterator result, 519 BinaryPredicate binary_pred, T*) { 520 T value = *first; 521 *result = value; 522 while (++first != last) 523 if (!binary_pred(value, *first)) { 524 value = *first; 525 *++result = value; 526 } 527 return ++result; 528 } 529 530 template <class InputIterator, class OutputIterator, class BinaryPredicate> 531 inline OutputIterator __unique_copy(InputIterator first, InputIterator last, 532 OutputIterator result, 533 BinaryPredicate binary_pred, 534 output_iterator_tag) { 535 return __unique_copy(first, last, result, binary_pred, value_type(first)); 536 } 537 538 template <class InputIterator, class OutputIterator, class BinaryPredicate> 539 inline OutputIterator unique_copy(InputIterator first, InputIterator last, 540 OutputIterator result, 541 BinaryPredicate binary_pred) { 542 if (first == last) return result; 543 return __unique_copy(first, last, result, binary_pred, 544 iterator_category(result)); 545 } 546 547 // 删除所有相邻重复元素 548 template <class ForwardIterator> 549 ForwardIterator unique(ForwardIterator first, ForwardIterator last) 550 { 551 first = adjacent_find(first, last); 552 return unique_copy(first, last, first); 553 } 554 555 // 好吧, 删除所有相邻重复元素, 并拷贝到指定位置 556 template <class ForwardIterator, class BinaryPredicate> 557 ForwardIterator unique(ForwardIterator first, ForwardIterator last, 558 BinaryPredicate binary_pred) 559 { 560 first = adjacent_find(first, last, binary_pred); 561 return unique_copy(first, last, first, binary_pred); 562 } 563 564 template <class BidirectionalIterator> 565 void __reverse(BidirectionalIterator first, BidirectionalIterator last, 566 bidirectional_iterator_tag) 567 { 568 while (true) 569 if (first == last || first == --last) 570 return; 571 else 572 iter_swap(first++, last); 573 } 574 575 template <class RandomAccessIterator> 576 void __reverse(RandomAccessIterator first, RandomAccessIterator last, 577 random_access_iterator_tag) 578 { 579 while (first < last) iter_swap(first++, --last); 580 } 581 582 // 将[first, last)内的元素倒置 583 // 还是为了效率进行函数派发, 不做解释了 584 template <class BidirectionalIterator> 585 inline void reverse(BidirectionalIterator first, BidirectionalIterator last) 586 { 587 __reverse(first, last, iterator_category(first)); 588 } 589 590 // 好吧, 和reverse的区别是会把处理后的元素拷贝到新区间 591 template <class BidirectionalIterator, class OutputIterator> 592 OutputIterator reverse_copy(BidirectionalIterator first, 593 BidirectionalIterator last, 594 OutputIterator result) 595 { 596 while (first != last) { 597 --last; 598 *result = *last; 599 ++result; 600 } 601 return result; 602 } 603 604 template <class ForwardIterator, class Distance> 605 void __rotate(ForwardIterator first, ForwardIterator middle, 606 ForwardIterator last, Distance*, forward_iterator_tag) { 607 for (ForwardIterator i = middle; ;) { 608 iter_swap(first, i); 609 ++first; 610 ++i; 611 if (first == middle) { 612 if (i == last) return; 613 middle = i; 614 } 615 else if (i == last) 616 i = middle; 617 } 618 } 619 620 template <class BidirectionalIterator, class Distance> 621 void __rotate(BidirectionalIterator first, BidirectionalIterator middle, 622 BidirectionalIterator last, Distance*, 623 bidirectional_iterator_tag) { 624 reverse(first, middle); 625 reverse(middle, last); 626 reverse(first, last); 627 } 628 629 // 这个你要是都不知道那就马上去学习数据结构的知识吧 630 template <class EuclideanRingElement> 631 EuclideanRingElement __gcd(EuclideanRingElement m, EuclideanRingElement n) 632 { 633 while (n != 0) { 634 EuclideanRingElement t = m % n; 635 m = n; 636 n = t; 637 } 638 return m; 639 } 640 641 template <class RandomAccessIterator, class Distance, class T> 642 void __rotate_cycle(RandomAccessIterator first, RandomAccessIterator last, 643 RandomAccessIterator initial, Distance shift, T*) { 644 T value = *initial; 645 RandomAccessIterator ptr1 = initial; 646 RandomAccessIterator ptr2 = ptr1 + shift; 647 while (ptr2 != initial) { 648 *ptr1 = *ptr2; 649 ptr1 = ptr2; 650 if (last - ptr2 > shift) 651 ptr2 += shift; 652 else 653 ptr2 = first + (shift - (last - ptr2)); 654 } 655 *ptr1 = value; 656 } 657 658 template <class RandomAccessIterator, class Distance> 659 void __rotate(RandomAccessIterator first, RandomAccessIterator middle, 660 RandomAccessIterator last, Distance*, 661 random_access_iterator_tag) { 662 Distance n = __gcd(last - first, middle - first); 663 while (n--) 664 __rotate_cycle(first, last, first + n, middle - first, 665 value_type(first)); 666 } 667 668 // 将[first, middle)和[middle, last)内元素互换 669 // 还是为了效率, 进行函数派发, 不解释了 670 template <class ForwardIterator> 671 inline void rotate(ForwardIterator first, ForwardIterator middle, 672 ForwardIterator last) { 673 if (first == middle || middle == last) return; 674 __rotate(first, middle, last, distance_type(first), 675 iterator_category(first)); 676 } 677 678 // 和rotate唯一的区别就是将旋转后的元素拷贝到新位置 679 template <class ForwardIterator, class OutputIterator> 680 OutputIterator rotate_copy(ForwardIterator first, ForwardIterator middle, 681 ForwardIterator last, OutputIterator result) { 682 return copy(first, middle, copy(middle, last, result)); 683 } 684 685 template <class RandomAccessIterator, class Distance> 686 void __random_shuffle(RandomAccessIterator first, RandomAccessIterator last, 687 Distance*) { 688 if (first == last) return; 689 for (RandomAccessIterator i = first + 1; i != last; ++i) 690 #ifdef __STL_NO_DRAND48 691 iter_swap(i, first + Distance(rand() % ((i - first) + 1))); 692 #else 693 iter_swap(i, first + Distance(lrand48() % ((i - first) + 1))); 694 #endif 695 } 696 697 template <class RandomAccessIterator> 698 inline void random_shuffle(RandomAccessIterator first, 699 RandomAccessIterator last) { 700 __random_shuffle(first, last, distance_type(first)); 701 } 702 703 // 产生随机的排列 704 template <class RandomAccessIterator, class RandomNumberGenerator> 705 void random_shuffle(RandomAccessIterator first, RandomAccessIterator last, 706 RandomNumberGenerator& rand) 707 { 708 if (first == last) return; 709 for (RandomAccessIterator i = first + 1; i != last; ++i) 710 iter_swap(i, first + rand((i - first) + 1)); 711 } 712 713 template <class ForwardIterator, class OutputIterator, class Distance> 714 OutputIterator random_sample_n(ForwardIterator first, ForwardIterator last, 715 OutputIterator out, const Distance n) 716 { 717 Distance remaining = 0; 718 distance(first, last, remaining); 719 Distance m = min(n, remaining); 720 721 while (m > 0) { 722 #ifdef __STL_NO_DRAND48 723 if (rand() % remaining < m) { 724 #else 725 if (lrand48() % remaining < m) { 726 #endif 727 *out = *first; 728 ++out; 729 --m; 730 } 731 732 --remaining; 733 ++first; 734 } 735 return out; 736 } 737 738 template <class ForwardIterator, class OutputIterator, class Distance, 739 class RandomNumberGenerator> 740 OutputIterator random_sample_n(ForwardIterator first, ForwardIterator last, 741 OutputIterator out, const Distance n, 742 RandomNumberGenerator& rand) 743 { 744 Distance remaining = 0; 745 distance(first, last, remaining); 746 Distance m = min(n, remaining); 747 748 while (m > 0) { 749 if (rand(remaining) < m) { 750 *out = *first; 751 ++out; 752 --m; 753 } 754 755 --remaining; 756 ++first; 757 } 758 return out; 759 } 760 761 template <class InputIterator, class RandomAccessIterator, class Distance> 762 RandomAccessIterator __random_sample(InputIterator first, InputIterator last, 763 RandomAccessIterator out, 764 const Distance n) 765 { 766 Distance m = 0; 767 Distance t = n; 768 for ( ; first != last && m < n; ++m, ++first) 769 out[m] = *first; 770 771 while (first != last) { 772 ++t; 773 #ifdef __STL_NO_DRAND48 774 Distance M = rand() % t; 775 #else 776 Distance M = lrand48() % t; 777 #endif 778 if (M < n) 779 out[M] = *first; 780 ++first; 781 } 782 783 return out + m; 784 } 785 786 template <class InputIterator, class RandomAccessIterator, 787 class RandomNumberGenerator, class Distance> 788 RandomAccessIterator __random_sample(InputIterator first, InputIterator last, 789 RandomAccessIterator out, 790 RandomNumberGenerator& rand, 791 const Distance n) 792 { 793 Distance m = 0; 794 Distance t = n; 795 for ( ; first != last && m < n; ++m, ++first) 796 out[m] = *first; 797 798 while (first != last) { 799 ++t; 800 Distance M = rand(t); 801 if (M < n) 802 out[M] = *first; 803 ++first; 804 } 805 806 return out + m; 807 } 808 809 template <class InputIterator, class RandomAccessIterator> 810 inline RandomAccessIterator 811 random_sample(InputIterator first, InputIterator last, 812 RandomAccessIterator out_first, RandomAccessIterator out_last) 813 { 814 return __random_sample(first, last, out_first, out_last - out_first); 815 } 816 817 template <class InputIterator, class RandomAccessIterator, 818 class RandomNumberGenerator> 819 inline RandomAccessIterator 820 random_sample(InputIterator first, InputIterator last, 821 RandomAccessIterator out_first, RandomAccessIterator out_last, 822 RandomNumberGenerator& rand) 823 { 824 return __random_sample(first, last, out_first, rand, out_last - out_first); 825 } 826 827 828 // 将[first, last)区间内元素重新排序, 所有满足判别式的元素都被放在前面 829 template <class BidirectionalIterator, class Predicate> 830 BidirectionalIterator partition(BidirectionalIterator first, 831 BidirectionalIterator last, Predicate pred) 832 { 833 while (true) { 834 while (true) 835 if (first == last) 836 return first; 837 else if (pred(*first)) 838 ++first; 839 else 840 break; 841 --last; 842 while (true) 843 if (first == last) 844 return first; 845 else if (!pred(*last)) 846 --last; 847 else 848 break; 849 iter_swap(first, last); 850 ++first; 851 } 852 } 853 854 template <class ForwardIterator, class Predicate, class Distance> 855 ForwardIterator __inplace_stable_partition(ForwardIterator first, 856 ForwardIterator last, 857 Predicate pred, Distance len) { 858 if (len == 1) return pred(*first) ? last : first; 859 ForwardIterator middle = first; 860 advance(middle, len / 2); 861 ForwardIterator 862 first_cut = __inplace_stable_partition(first, middle, pred, len / 2); 863 ForwardIterator 864 second_cut = __inplace_stable_partition(middle, last, pred, 865 len - len / 2); 866 rotate(first_cut, middle, second_cut); 867 len = 0; 868 distance(middle, second_cut, len); 869 advance(first_cut, len); 870 return first_cut; 871 } 872 873 template <class ForwardIterator, class Pointer, class Predicate, 874 class Distance> 875 ForwardIterator __stable_partition_adaptive(ForwardIterator first, 876 ForwardIterator last, 877 Predicate pred, Distance len, 878 Pointer buffer, 879 Distance buffer_size) { 880 if (len <= buffer_size) { 881 ForwardIterator result1 = first; 882 Pointer result2 = buffer; 883 for ( ; first != last ; ++first) 884 if (pred(*first)) { 885 *result1 = *first; 886 ++result1; 887 } 888 else { 889 *result2 = *first; 890 ++result2; 891 } 892 copy(buffer, result2, result1); 893 return result1; 894 } 895 else { 896 ForwardIterator middle = first; 897 advance(middle, len / 2); 898 ForwardIterator first_cut = 899 __stable_partition_adaptive(first, middle, pred, len / 2, 900 buffer, buffer_size); 901 ForwardIterator second_cut = 902 __stable_partition_adaptive(middle, last, pred, len - len / 2, 903 buffer, buffer_size); 904 905 rotate(first_cut, middle, second_cut); 906 len = 0; 907 distance(middle, second_cut, len); 908 advance(first_cut, len); 909 return first_cut; 910 } 911 } 912 913 template <class ForwardIterator, class Predicate, class T, class Distance> 914 inline ForwardIterator __stable_partition_aux(ForwardIterator first, 915 ForwardIterator last, 916 Predicate pred, T*, Distance*) { 917 temporary_buffer<ForwardIterator, T> buf(first, last); 918 if (buf.size() > 0) 919 return __stable_partition_adaptive(first, last, pred, 920 Distance(buf.requested_size()), 921 buf.begin(), buf.size()); 922 else 923 return __inplace_stable_partition(first, last, pred, 924 Distance(buf.requested_size())); 925 } 926 927 template <class ForwardIterator, class Predicate> 928 inline ForwardIterator stable_partition(ForwardIterator first, 929 ForwardIterator last, 930 Predicate pred) { 931 if (first == last) 932 return first; 933 else 934 return __stable_partition_aux(first, last, pred, 935 value_type(first), distance_type(first)); 936 } 937 938 template <class RandomAccessIterator, class T> 939 RandomAccessIterator __unguarded_partition(RandomAccessIterator first, 940 RandomAccessIterator last, 941 T pivot) { 942 while (true) { 943 while (*first < pivot) ++first; 944 --last; 945 while (pivot < *last) --last; 946 if (!(first < last)) return first; 947 iter_swap(first, last); 948 ++first; 949 } 950 } 951 952 template <class RandomAccessIterator, class T, class Compare> 953 RandomAccessIterator __unguarded_partition(RandomAccessIterator first, 954 RandomAccessIterator last, 955 T pivot, Compare comp) { 956 while (1) { 957 while (comp(*first, pivot)) ++first; 958 --last; 959 while (comp(pivot, *last)) --last; 960 if (!(first < last)) return first; 961 iter_swap(first, last); 962 ++first; 963 } 964 } 965 966 const int __stl_threshold = 16; 967 968 969 template <class RandomAccessIterator, class T> 970 void __unguarded_linear_insert(RandomAccessIterator last, T value) { 971 RandomAccessIterator next = last; 972 --next; 973 while (value < *next) { 974 *last = *next; 975 last = next; 976 --next; 977 } 978 *last = value; 979 } 980 981 template <class RandomAccessIterator, class T, class Compare> 982 void __unguarded_linear_insert(RandomAccessIterator last, T value, 983 Compare comp) { 984 RandomAccessIterator next = last; 985 --next; 986 while (comp(value , *next)) { 987 *last = *next; 988 last = next; 989 --next; 990 } 991 *last = value; 992 } 993 994 template <class RandomAccessIterator, class T> 995 inline void __linear_insert(RandomAccessIterator first, 996 RandomAccessIterator last, T*) { 997 T value = *last; 998 if (value < *first) { 999 copy_backward(first, last, last + 1); 1000 *first = value; 1001 } 1002 else 1003 __unguarded_linear_insert(last, value); 1004 } 1005 1006 template <class RandomAccessIterator, class T, class Compare> 1007 inline void __linear_insert(RandomAccessIterator first, 1008 RandomAccessIterator last, T*, Compare comp) { 1009 T value = *last; 1010 if (comp(value, *first)) { 1011 copy_backward(first, last, last + 1); 1012 *first = value; 1013 } 1014 else 1015 __unguarded_linear_insert(last, value, comp); 1016 } 1017 1018 template <class RandomAccessIterator> 1019 void __insertion_sort(RandomAccessIterator first, RandomAccessIterator last) { 1020 if (first == last) return; 1021 for (RandomAccessIterator i = first + 1; i != last; ++i) 1022 __linear_insert(first, i, value_type(first)); 1023 } 1024 1025 template <class RandomAccessIterator, class Compare> 1026 void __insertion_sort(RandomAccessIterator first, 1027 RandomAccessIterator last, Compare comp) { 1028 if (first == last) return; 1029 for (RandomAccessIterator i = first + 1; i != last; ++i) 1030 __linear_insert(first, i, value_type(first), comp); 1031 } 1032 1033 template <class RandomAccessIterator, class T> 1034 void __unguarded_insertion_sort_aux(RandomAccessIterator first, 1035 RandomAccessIterator last, T*) { 1036 for (RandomAccessIterator i = first; i != last; ++i) 1037 __unguarded_linear_insert(i, T(*i)); 1038 } 1039 1040 template <class RandomAccessIterator> 1041 inline void __unguarded_insertion_sort(RandomAccessIterator first, 1042 RandomAccessIterator last) { 1043 __unguarded_insertion_sort_aux(first, last, value_type(first)); 1044 } 1045 1046 template <class RandomAccessIterator, class T, class Compare> 1047 void __unguarded_insertion_sort_aux(RandomAccessIterator first, 1048 RandomAccessIterator last, 1049 T*, Compare comp) { 1050 for (RandomAccessIterator i = first; i != last; ++i) 1051 __unguarded_linear_insert(i, T(*i), comp); 1052 } 1053 1054 template <class RandomAccessIterator, class Compare> 1055 inline void __unguarded_insertion_sort(RandomAccessIterator first, 1056 RandomAccessIterator last, 1057 Compare comp) { 1058 __unguarded_insertion_sort_aux(first, last, value_type(first), comp); 1059 } 1060 1061 template <class RandomAccessIterator> 1062 void __final_insertion_sort(RandomAccessIterator first, 1063 RandomAccessIterator last) { 1064 if (last - first > __stl_threshold) { 1065 __insertion_sort(first, first + __stl_threshold); 1066 __unguarded_insertion_sort(first + __stl_threshold, last); 1067 } 1068 else 1069 __insertion_sort(first, last); 1070 } 1071 1072 template <class RandomAccessIterator, class Compare> 1073 void __final_insertion_sort(RandomAccessIterator first, 1074 RandomAccessIterator last, Compare comp) { 1075 if (last - first > __stl_threshold) { 1076 __insertion_sort(first, first + __stl_threshold, comp); 1077 __unguarded_insertion_sort(first + __stl_threshold, last, comp); 1078 } 1079 else 1080 __insertion_sort(first, last, comp); 1081 } 1082 1083 template <class Size> 1084 inline Size __lg(Size n) { 1085 Size k; 1086 for (k = 0; n > 1; n >>= 1) ++k; 1087 return k; 1088 } 1089 1090 template <class RandomAccessIterator, class T, class Size> 1091 void __introsort_loop(RandomAccessIterator first, 1092 RandomAccessIterator last, T*, 1093 Size depth_limit) { 1094 while (last - first > __stl_threshold) { 1095 if (depth_limit == 0) { 1096 partial_sort(first, last, last); 1097 return; 1098 } 1099 --depth_limit; 1100 RandomAccessIterator cut = __unguarded_partition 1101 (first, last, T(__median(*first, *(first + (last - first)/2), 1102 *(last - 1)))); 1103 __introsort_loop(cut, last, value_type(first), depth_limit); 1104 last = cut; 1105 } 1106 } 1107 1108 template <class RandomAccessIterator, class T, class Size, class Compare> 1109 void __introsort_loop(RandomAccessIterator first, 1110 RandomAccessIterator last, T*, 1111 Size depth_limit, Compare comp) { 1112 while (last - first > __stl_threshold) { 1113 if (depth_limit == 0) { 1114 partial_sort(first, last, last, comp); 1115 return; 1116 } 1117 --depth_limit; 1118 RandomAccessIterator cut = __unguarded_partition 1119 (first, last, T(__median(*first, *(first + (last - first)/2), 1120 *(last - 1), comp)), comp); 1121 __introsort_loop(cut, last, value_type(first), depth_limit, comp); 1122 last = cut; 1123 } 1124 } 1125 1126 // 必须为随RandomAccessIterator, 排序算法要根据情况进行派发 1127 template <class RandomAccessIterator> 1128 inline void sort(RandomAccessIterator first, RandomAccessIterator last) 1129 { 1130 if (first != last) { 1131 __introsort_loop(first, last, value_type(first), __lg(last - first) * 2); 1132 __final_insertion_sort(first, last); 1133 } 1134 } 1135 1136 template <class RandomAccessIterator, class Compare> 1137 inline void sort(RandomAccessIterator first, RandomAccessIterator last, 1138 Compare comp) { 1139 if (first != last) { 1140 __introsort_loop(first, last, value_type(first), __lg(last - first) * 2, 1141 comp); 1142 __final_insertion_sort(first, last, comp); 1143 } 1144 } 1145 1146 1147 template <class RandomAccessIterator> 1148 void __inplace_stable_sort(RandomAccessIterator first, 1149 RandomAccessIterator last) { 1150 if (last - first < 15) { 1151 __insertion_sort(first, last); 1152 return; 1153 } 1154 RandomAccessIterator middle = first + (last - first) / 2; 1155 __inplace_stable_sort(first, middle); 1156 __inplace_stable_sort(middle, last); 1157 __merge_without_buffer(first, middle, last, middle - first, last - middle); 1158 } 1159 1160 template <class RandomAccessIterator, class Compare> 1161 void __inplace_stable_sort(RandomAccessIterator first, 1162 RandomAccessIterator last, Compare comp) { 1163 if (last - first < 15) { 1164 __insertion_sort(first, last, comp); 1165 return; 1166 } 1167 RandomAccessIterator middle = first + (last - first) / 2; 1168 __inplace_stable_sort(first, middle, comp); 1169 __inplace_stable_sort(middle, last, comp); 1170 __merge_without_buffer(first, middle, last, middle - first, 1171 last - middle, comp); 1172 } 1173 1174 template <class RandomAccessIterator1, class RandomAccessIterator2, 1175 class Distance> 1176 void __merge_sort_loop(RandomAccessIterator1 first, 1177 RandomAccessIterator1 last, 1178 RandomAccessIterator2 result, Distance step_size) { 1179 Distance two_step = 2 * step_size; 1180 1181 while (last - first >= two_step) { 1182 result = merge(first, first + step_size, 1183 first + step_size, first + two_step, result); 1184 first += two_step; 1185 } 1186 1187 step_size = min(Distance(last - first), step_size); 1188 merge(first, first + step_size, first + step_size, last, result); 1189 } 1190 1191 template <class RandomAccessIterator1, class RandomAccessIterator2, 1192 class Distance, class Compare> 1193 void __merge_sort_loop(RandomAccessIterator1 first, 1194 RandomAccessIterator1 last, 1195 RandomAccessIterator2 result, Distance step_size, 1196 Compare comp) { 1197 Distance two_step = 2 * step_size; 1198 1199 while (last - first >= two_step) { 1200 result = merge(first, first + step_size, 1201 first + step_size, first + two_step, result, comp); 1202 first += two_step; 1203 } 1204 step_size = min(Distance(last - first), step_size); 1205 1206 merge(first, first + step_size, first + step_size, last, result, comp); 1207 } 1208 1209 const int __stl_chunk_size = 7; 1210 1211 template <class RandomAccessIterator, class Distance> 1212 void __chunk_insertion_sort(RandomAccessIterator first, 1213 RandomAccessIterator last, Distance chunk_size) { 1214 while (last - first >= chunk_size) { 1215 __insertion_sort(first, first + chunk_size); 1216 first += chunk_size; 1217 } 1218 __insertion_sort(first, last); 1219 } 1220 1221 template <class RandomAccessIterator, class Distance, class Compare> 1222 void __chunk_insertion_sort(RandomAccessIterator first, 1223 RandomAccessIterator last, 1224 Distance chunk_size, Compare comp) { 1225 while (last - first >= chunk_size) { 1226 __insertion_sort(first, first + chunk_size, comp); 1227 first += chunk_size; 1228 } 1229 __insertion_sort(first, last, comp); 1230 } 1231 1232 template <class RandomAccessIterator, class Pointer, class Distance> 1233 void __merge_sort_with_buffer(RandomAccessIterator first, 1234 RandomAccessIterator last, 1235 Pointer buffer, Distance*) { 1236 Distance len = last - first; 1237 Pointer buffer_last = buffer + len; 1238 1239 Distance step_size = __stl_chunk_size; 1240 __chunk_insertion_sort(first, last, step_size); 1241 1242 while (step_size < len) { 1243 __merge_sort_loop(first, last, buffer, step_size); 1244 step_size *= 2; 1245 __merge_sort_loop(buffer, buffer_last, first, step_size); 1246 step_size *= 2; 1247 } 1248 } 1249 1250 template <class RandomAccessIterator, class Pointer, class Distance, 1251 class Compare> 1252 void __merge_sort_with_buffer(RandomAccessIterator first, 1253 RandomAccessIterator last, Pointer buffer, 1254 Distance*, Compare comp) { 1255 Distance len = last - first; 1256 Pointer buffer_last = buffer + len; 1257 1258 Distance step_size = __stl_chunk_size; 1259 __chunk_insertion_sort(first, last, step_size, comp); 1260 1261 while (step_size < len) { 1262 __merge_sort_loop(first, last, buffer, step_size, comp); 1263 step_size *= 2; 1264 __merge_sort_loop(buffer, buffer_last, first, step_size, comp); 1265 step_size *= 2; 1266 } 1267 } 1268 1269 template <class RandomAccessIterator, class Pointer, class Distance> 1270 void __stable_sort_adaptive(RandomAccessIterator first, 1271 RandomAccessIterator last, Pointer buffer, 1272 Distance buffer_size) { 1273 Distance len = (last - first + 1) / 2; 1274 RandomAccessIterator middle = first + len; 1275 if (len > buffer_size) { 1276 __stable_sort_adaptive(first, middle, buffer, buffer_size); 1277 __stable_sort_adaptive(middle, last, buffer, buffer_size); 1278 } else { 1279 __merge_sort_with_buffer(first, middle, buffer, (Distance*)0); 1280 __merge_sort_with_buffer(middle, last, buffer, (Distance*)0); 1281 } 1282 __merge_adaptive(first, middle, last, Distance(middle - first), 1283 Distance(last - middle), buffer, buffer_size); 1284 } 1285 1286 template <class RandomAccessIterator, class Pointer, class Distance, 1287 class Compare> 1288 void __stable_sort_adaptive(RandomAccessIterator first, 1289 RandomAccessIterator last, Pointer buffer, 1290 Distance buffer_size, Compare comp) { 1291 Distance len = (last - first + 1) / 2; 1292 RandomAccessIterator middle = first + len; 1293 if (len > buffer_size) { 1294 __stable_sort_adaptive(first, middle, buffer, buffer_size, 1295 comp); 1296 __stable_sort_adaptive(middle, last, buffer, buffer_size, 1297 comp); 1298 } else { 1299 __merge_sort_with_buffer(first, middle, buffer, (Distance*)0, comp); 1300 __merge_sort_with_buffer(middle, last, buffer, (Distance*)0, comp); 1301 } 1302 __merge_adaptive(first, middle, last, Distance(middle - first), 1303 Distance(last - middle), buffer, buffer_size, 1304 comp); 1305 } 1306 1307 template <class RandomAccessIterator, class T, class Distance> 1308 inline void __stable_sort_aux(RandomAccessIterator first, 1309 RandomAccessIterator last, T*, Distance*) { 1310 temporary_buffer<RandomAccessIterator, T> buf(first, last); 1311 if (buf.begin() == 0) 1312 __inplace_stable_sort(first, last); 1313 else 1314 __stable_sort_adaptive(first, last, buf.begin(), Distance(buf.size())); 1315 } 1316 1317 template <class RandomAccessIterator, class T, class Distance, class Compare> 1318 inline void __stable_sort_aux(RandomAccessIterator first, 1319 RandomAccessIterator last, T*, Distance*, 1320 Compare comp) { 1321 temporary_buffer<RandomAccessIterator, T> buf(first, last); 1322 if (buf.begin() == 0) 1323 __inplace_stable_sort(first, last, comp); 1324 else 1325 __stable_sort_adaptive(first, last, buf.begin(), Distance(buf.size()), 1326 comp); 1327 } 1328 1329 template <class RandomAccessIterator> 1330 inline void stable_sort(RandomAccessIterator first, 1331 RandomAccessIterator last) { 1332 __stable_sort_aux(first, last, value_type(first), distance_type(first)); 1333 } 1334 1335 template <class RandomAccessIterator, class Compare> 1336 inline void stable_sort(RandomAccessIterator first, 1337 RandomAccessIterator last, Compare comp) { 1338 __stable_sort_aux(first, last, value_type(first), distance_type(first), 1339 comp); 1340 } 1341 1342 template <class RandomAccessIterator, class T> 1343 void __partial_sort(RandomAccessIterator first, RandomAccessIterator middle, 1344 RandomAccessIterator last, T*) { 1345 make_heap(first, middle); 1346 for (RandomAccessIterator i = middle; i < last; ++i) 1347 if (*i < *first) 1348 __pop_heap(first, middle, i, T(*i), distance_type(first)); 1349 sort_heap(first, middle); 1350 } 1351 1352 // 只保证[first, middle)有序, 效率至上时使用 1353 template <class RandomAccessIterator> 1354 inline void partial_sort(RandomAccessIterator first, 1355 RandomAccessIterator middle, 1356 RandomAccessIterator last) 1357 { 1358 __partial_sort(first, middle, last, value_type(first)); 1359 } 1360 1361 template <class RandomAccessIterator, class T, class Compare> 1362 void __partial_sort(RandomAccessIterator first, RandomAccessIterator middle, 1363 RandomAccessIterator last, T*, Compare comp) { 1364 make_heap(first, middle, comp); 1365 for (RandomAccessIterator i = middle; i < last; ++i) 1366 if (comp(*i, *first)) 1367 __pop_heap(first, middle, i, T(*i), comp, distance_type(first)); 1368 sort_heap(first, middle, comp); 1369 } 1370 1371 template <class RandomAccessIterator, class Compare> 1372 inline void partial_sort(RandomAccessIterator first, 1373 RandomAccessIterator middle, 1374 RandomAccessIterator last, Compare comp) { 1375 __partial_sort(first, middle, last, value_type(first), comp); 1376 } 1377 1378 template <class InputIterator, class RandomAccessIterator, class Distance, 1379 class T> 1380 RandomAccessIterator __partial_sort_copy(InputIterator first, 1381 InputIterator last, 1382 RandomAccessIterator result_first, 1383 RandomAccessIterator result_last, 1384 Distance*, T*) { 1385 if (result_first == result_last) return result_last; 1386 RandomAccessIterator result_real_last = result_first; 1387 while(first != last && result_real_last != result_last) { 1388 *result_real_last = *first; 1389 ++result_real_last; 1390 ++first; 1391 } 1392 make_heap(result_first, result_real_last); 1393 while (first != last) { 1394 if (*first < *result_first) 1395 __adjust_heap(result_first, Distance(0), 1396 Distance(result_real_last - result_first), T(*first)); 1397 ++first; 1398 } 1399 sort_heap(result_first, result_real_last); 1400 return result_real_last; 1401 } 1402 1403 template <class InputIterator, class RandomAccessIterator> 1404 inline RandomAccessIterator 1405 partial_sort_copy(InputIterator first, InputIterator last, 1406 RandomAccessIterator result_first, 1407 RandomAccessIterator result_last) { 1408 return __partial_sort_copy(first, last, result_first, result_last, 1409 distance_type(result_first), value_type(first)); 1410 } 1411 1412 template <class InputIterator, class RandomAccessIterator, class Compare, 1413 class Distance, class T> 1414 RandomAccessIterator __partial_sort_copy(InputIterator first, 1415 InputIterator last, 1416 RandomAccessIterator result_first, 1417 RandomAccessIterator result_last, 1418 Compare comp, Distance*, T*) { 1419 if (result_first == result_last) return result_last; 1420 RandomAccessIterator result_real_last = result_first; 1421 while(first != last && result_real_last != result_last) { 1422 *result_real_last = *first; 1423 ++result_real_last; 1424 ++first; 1425 } 1426 make_heap(result_first, result_real_last, comp); 1427 while (first != last) { 1428 if (comp(*first, *result_first)) 1429 __adjust_heap(result_first, Distance(0), 1430 Distance(result_real_last - result_first), T(*first), 1431 comp); 1432 ++first; 1433 } 1434 sort_heap(result_first, result_real_last, comp); 1435 return result_real_last; 1436 } 1437 1438 template <class InputIterator, class RandomAccessIterator, class Compare> 1439 inline RandomAccessIterator 1440 partial_sort_copy(InputIterator first, InputIterator last, 1441 RandomAccessIterator result_first, 1442 RandomAccessIterator result_last, Compare comp) { 1443 return __partial_sort_copy(first, last, result_first, result_last, comp, 1444 distance_type(result_first), value_type(first)); 1445 } 1446 1447 template <class RandomAccessIterator, class T> 1448 void __nth_element(RandomAccessIterator first, RandomAccessIterator nth, 1449 RandomAccessIterator last, T*) { 1450 while (last - first > 3) { 1451 RandomAccessIterator cut = __unguarded_partition 1452 (first, last, T(__median(*first, *(first + (last - first)/2), 1453 *(last - 1)))); 1454 if (cut <= nth) 1455 first = cut; 1456 else 1457 last = cut; 1458 } 1459 __insertion_sort(first, last); 1460 } 1461 1462 template <class RandomAccessIterator> 1463 inline void nth_element(RandomAccessIterator first, RandomAccessIterator nth, 1464 RandomAccessIterator last) { 1465 __nth_element(first, nth, last, value_type(first)); 1466 } 1467 1468 template <class RandomAccessIterator, class T, class Compare> 1469 void __nth_element(RandomAccessIterator first, RandomAccessIterator nth, 1470 RandomAccessIterator last, T*, Compare comp) { 1471 while (last - first > 3) { 1472 RandomAccessIterator cut = __unguarded_partition 1473 (first, last, T(__median(*first, *(first + (last - first)/2), 1474 *(last - 1), comp)), comp); 1475 if (cut <= nth) 1476 first = cut; 1477 else 1478 last = cut; 1479 } 1480 __insertion_sort(first, last, comp); 1481 } 1482 1483 template <class RandomAccessIterator, class Compare> 1484 inline void nth_element(RandomAccessIterator first, RandomAccessIterator nth, 1485 RandomAccessIterator last, Compare comp) { 1486 __nth_element(first, nth, last, value_type(first), comp); 1487 } 1488 1489 template <class ForwardIterator, class T, class Distance> 1490 ForwardIterator __lower_bound(ForwardIterator first, ForwardIterator last, 1491 const T& value, Distance*, 1492 forward_iterator_tag) { 1493 Distance len = 0; 1494 distance(first, last, len); 1495 Distance half; 1496 ForwardIterator middle; 1497 1498 while (len > 0) { 1499 half = len >> 1; 1500 middle = first; 1501 advance(middle, half); 1502 if (*middle < value) { 1503 first = middle; 1504 ++first; 1505 len = len - half - 1; 1506 } 1507 else 1508 len = half; 1509 } 1510 return first; 1511 } 1512 1513 template <class RandomAccessIterator, class T, class Distance> 1514 RandomAccessIterator __lower_bound(RandomAccessIterator first, 1515 RandomAccessIterator last, const T& value, 1516 Distance*, random_access_iterator_tag) { 1517 Distance len = last - first; 1518 Distance half; 1519 RandomAccessIterator middle; 1520 1521 while (len > 0) { 1522 half = len >> 1; 1523 middle = first + half; 1524 if (*middle < value) { 1525 first = middle + 1; 1526 len = len - half - 1; 1527 } 1528 else 1529 len = half; 1530 } 1531 return first; 1532 } 1533 1534 // 用于有序区间, 返回第一个大于value的位置 1535 // 同样为了效率, 要进行函数派发 1536 template <class ForwardIterator, class T> 1537 inline ForwardIterator lower_bound(ForwardIterator first, ForwardIterator last, 1538 const T& value) 1539 { 1540 return __lower_bound(first, last, value, distance_type(first), 1541 iterator_category(first)); 1542 } 1543 1544 template <class ForwardIterator, class T, class Compare, class Distance> 1545 ForwardIterator __lower_bound(ForwardIterator first, ForwardIterator last, 1546 const T& value, Compare comp, Distance*, 1547 forward_iterator_tag) { 1548 Distance len = 0; 1549 distance(first, last, len); 1550 Distance half; 1551 ForwardIterator middle; 1552 1553 while (len > 0) { 1554 half = len >> 1; 1555 middle = first; 1556 advance(middle, half); 1557 if (comp(*middle, value)) { 1558 first = middle; 1559 ++first; 1560 len = len - half - 1; 1561 } 1562 else 1563 len = half; 1564 } 1565 return first; 1566 } 1567 1568 template <class RandomAccessIterator, class T, class Compare, class Distance> 1569 RandomAccessIterator __lower_bound(RandomAccessIterator first, 1570 RandomAccessIterator last, 1571 const T& value, Compare comp, Distance*, 1572 random_access_iterator_tag) { 1573 Distance len = last - first; 1574 Distance half; 1575 RandomAccessIterator middle; 1576 1577 while (len > 0) { 1578 half = len >> 1; 1579 middle = first + half; 1580 if (comp(*middle, value)) { 1581 first = middle + 1; 1582 len = len - half - 1; 1583 } 1584 else 1585 len = half; 1586 } 1587 return first; 1588 } 1589 1590 template <class ForwardIterator, class T, class Compare> 1591 inline ForwardIterator lower_bound(ForwardIterator first, ForwardIterator last, 1592 const T& value, Compare comp) { 1593 return __lower_bound(first, last, value, comp, distance_type(first), 1594 iterator_category(first)); 1595 } 1596 1597 template <class ForwardIterator, class T, class Distance> 1598 ForwardIterator __upper_bound(ForwardIterator first, ForwardIterator last, 1599 const T& value, Distance*, 1600 forward_iterator_tag) { 1601 Distance len = 0; 1602 distance(first, last, len); 1603 Distance half; 1604 ForwardIterator middle; 1605 1606 while (len > 0) { 1607 half = len >> 1; 1608 middle = first; 1609 advance(middle, half); 1610 if (value < *middle) 1611 len = half; 1612 else { 1613 first = middle; 1614 ++first; 1615 len = len - half - 1; 1616 } 1617 } 1618 return first; 1619 } 1620 1621 template <class RandomAccessIterator, class T, class Distance> 1622 RandomAccessIterator __upper_bound(RandomAccessIterator first, 1623 RandomAccessIterator last, const T& value, 1624 Distance*, random_access_iterator_tag) { 1625 Distance len = last - first; 1626 Distance half; 1627 RandomAccessIterator middle; 1628 1629 while (len > 0) { 1630 half = len >> 1; 1631 middle = first + half; 1632 if (value < *middle) 1633 len = half; 1634 else { 1635 first = middle + 1; 1636 len = len - half - 1; 1637 } 1638 } 1639 return first; 1640 } 1641 1642 template <class ForwardIterator, class T> 1643 inline ForwardIterator upper_bound(ForwardIterator first, ForwardIterator last, 1644 const T& value) { 1645 return __upper_bound(first, last, value, distance_type(first), 1646 iterator_category(first)); 1647 } 1648 1649 template <class ForwardIterator, class T, class Compare, class Distance> 1650 ForwardIterator __upper_bound(ForwardIterator first, ForwardIterator last, 1651 const T& value, Compare comp, Distance*, 1652 forward_iterator_tag) { 1653 Distance len = 0; 1654 distance(first, last, len); 1655 Distance half; 1656 ForwardIterator middle; 1657 1658 while (len > 0) { 1659 half = len >> 1; 1660 middle = first; 1661 advance(middle, half); 1662 if (comp(value, *middle)) 1663 len = half; 1664 else { 1665 first = middle; 1666 ++first; 1667 len = len - half - 1; 1668 } 1669 } 1670 return first; 1671 } 1672 1673 template <class RandomAccessIterator, class T, class Compare, class Distance> 1674 RandomAccessIterator __upper_bound(RandomAccessIterator first, 1675 RandomAccessIterator last, 1676 const T& value, Compare comp, Distance*, 1677 random_access_iterator_tag) { 1678 Distance len = last - first; 1679 Distance half; 1680 RandomAccessIterator middle; 1681 1682 while (len > 0) { 1683 half = len >> 1; 1684 middle = first + half; 1685 if (comp(value, *middle)) 1686 len = half; 1687 else { 1688 first = middle + 1; 1689 len = len - half - 1; 1690 } 1691 } 1692 return first; 1693 } 1694 1695 template <class ForwardIterator, class T, class Compare> 1696 inline ForwardIterator upper_bound(ForwardIterator first, ForwardIterator last, 1697 const T& value, Compare comp) { 1698 return __upper_bound(first, last, value, comp, distance_type(first), 1699 iterator_category(first)); 1700 } 1701 1702 template <class ForwardIterator, class T, class Distance> 1703 pair<ForwardIterator, ForwardIterator> 1704 __equal_range(ForwardIterator first, ForwardIterator last, const T& value, 1705 Distance*, forward_iterator_tag) { 1706 Distance len = 0; 1707 distance(first, last, len); 1708 Distance half; 1709 ForwardIterator middle, left, right; 1710 1711 while (len > 0) { 1712 half = len >> 1; 1713 middle = first; 1714 advance(middle, half); 1715 if (*middle < value) { 1716 first = middle; 1717 ++first; 1718 len = len - half - 1; 1719 } 1720 else if (value < *middle) 1721 len = half; 1722 else { 1723 left = lower_bound(first, middle, value); 1724 advance(first, len); 1725 right = upper_bound(++middle, first, value); 1726 return pair<ForwardIterator, ForwardIterator>(left, right); 1727 } 1728 } 1729 return pair<ForwardIterator, ForwardIterator>(first, first); 1730 } 1731 1732 template <class RandomAccessIterator, class T, class Distance> 1733 pair<RandomAccessIterator, RandomAccessIterator> 1734 __equal_range(RandomAccessIterator first, RandomAccessIterator last, 1735 const T& value, Distance*, random_access_iterator_tag) { 1736 Distance len = last - first; 1737 Distance half; 1738 RandomAccessIterator middle, left, right; 1739 1740 while (len > 0) { 1741 half = len >> 1; 1742 middle = first + half; 1743 if (*middle < value) { 1744 first = middle + 1; 1745 len = len - half - 1; 1746 } 1747 else if (value < *middle) 1748 len = half; 1749 else { 1750 left = lower_bound(first, middle, value); 1751 right = upper_bound(++middle, first + len, value); 1752 return pair<RandomAccessIterator, RandomAccessIterator>(left, 1753 right); 1754 } 1755 } 1756 return pair<RandomAccessIterator, RandomAccessIterator>(first, first); 1757 } 1758 1759 template <class ForwardIterator, class T> 1760 inline pair<ForwardIterator, ForwardIterator> 1761 equal_range(ForwardIterator first, ForwardIterator last, const T& value) { 1762 return __equal_range(first, last, value, distance_type(first), 1763 iterator_category(first)); 1764 } 1765 1766 template <class ForwardIterator, class T, class Compare, class Distance> 1767 pair<ForwardIterator, ForwardIterator> 1768 __equal_range(ForwardIterator first, ForwardIterator last, const T& value, 1769 Compare comp, Distance*, forward_iterator_tag) { 1770 Distance len = 0; 1771 distance(first, last, len); 1772 Distance half; 1773 ForwardIterator middle, left, right; 1774 1775 while (len > 0) { 1776 half = len >> 1; 1777 middle = first; 1778 advance(middle, half); 1779 if (comp(*middle, value)) { 1780 first = middle; 1781 ++first; 1782 len = len - half - 1; 1783 } 1784 else if (comp(value, *middle)) 1785 len = half; 1786 else { 1787 left = lower_bound(first, middle, value, comp); 1788 advance(first, len); 1789 right = upper_bound(++middle, first, value, comp); 1790 return pair<ForwardIterator, ForwardIterator>(left, right); 1791 } 1792 } 1793 return pair<ForwardIterator, ForwardIterator>(first, first); 1794 } 1795 1796 template <class RandomAccessIterator, class T, class Compare, class Distance> 1797 pair<RandomAccessIterator, RandomAccessIterator> 1798 __equal_range(RandomAccessIterator first, RandomAccessIterator last, 1799 const T& value, Compare comp, Distance*, 1800 random_access_iterator_tag) { 1801 Distance len = last - first; 1802 Distance half; 1803 RandomAccessIterator middle, left, right; 1804 1805 while (len > 0) { 1806 half = len >> 1; 1807 middle = first + half; 1808 if (comp(*middle, value)) { 1809 first = middle + 1; 1810 len = len - half - 1; 1811 } 1812 else if (comp(value, *middle)) 1813 len = half; 1814 else { 1815 left = lower_bound(first, middle, value, comp); 1816 right = upper_bound(++middle, first + len, value, comp); 1817 return pair<RandomAccessIterator, RandomAccessIterator>(left, 1818 right); 1819 } 1820 } 1821 return pair<RandomAccessIterator, RandomAccessIterator>(first, first); 1822 } 1823 1824 template <class ForwardIterator, class T, class Compare> 1825 inline pair<ForwardIterator, ForwardIterator> 1826 equal_range(ForwardIterator first, ForwardIterator last, const T& value, 1827 Compare comp) { 1828 return __equal_range(first, last, value, comp, distance_type(first), 1829 iterator_category(first)); 1830 } 1831 1832 // 用于有序区间的二分查找, 不知道的赶快去学数据结构 1833 template <class ForwardIterator, class T> 1834 bool binary_search(ForwardIterator first, ForwardIterator last, 1835 const T& value) { 1836 ForwardIterator i = lower_bound(first, last, value); 1837 return i != last && !(value < *i); 1838 } 1839 1840 template <class ForwardIterator, class T, class Compare> 1841 bool binary_search(ForwardIterator first, ForwardIterator last, const T& value, 1842 Compare comp) { 1843 ForwardIterator i = lower_bound(first, last, value, comp); 1844 return i != last && !comp(value, *i); 1845 } 1846 1847 // 将两个有序区间合并起来, 并保证其也有序 1848 template <class InputIterator1, class InputIterator2, class OutputIterator> 1849 OutputIterator merge(InputIterator1 first1, InputIterator1 last1, 1850 InputIterator2 first2, InputIterator2 last2, 1851 OutputIterator result) 1852 { 1853 while (first1 != last1 && first2 != last2) { 1854 if (*first2 < *first1) { 1855 *result = *first2; 1856 ++first2; 1857 } 1858 else { 1859 *result = *first1; 1860 ++first1; 1861 } 1862 ++result; 1863 } 1864 return copy(first2, last2, copy(first1, last1, result)); 1865 } 1866 1867 template <class InputIterator1, class InputIterator2, class OutputIterator, 1868 class Compare> 1869 OutputIterator merge(InputIterator1 first1, InputIterator1 last1, 1870 InputIterator2 first2, InputIterator2 last2, 1871 OutputIterator result, Compare comp) 1872 { 1873 while (first1 != last1 && first2 != last2) { 1874 if (comp(*first2, *first1)) { 1875 *result = *first2; 1876 ++first2; 1877 } 1878 else { 1879 *result = *first1; 1880 ++first1; 1881 } 1882 ++result; 1883 } 1884 return copy(first2, last2, copy(first1, last1, result)); 1885 } 1886 1887 template <class BidirectionalIterator, class Distance> 1888 void __merge_without_buffer(BidirectionalIterator first, 1889 BidirectionalIterator middle, 1890 BidirectionalIterator last, 1891 Distance len1, Distance len2) { 1892 if (len1 == 0 || len2 == 0) return; 1893 if (len1 + len2 == 2) { 1894 if (*middle < *first) iter_swap(first, middle); 1895 return; 1896 } 1897 BidirectionalIterator first_cut = first; 1898 BidirectionalIterator second_cut = middle; 1899 Distance len11 = 0; 1900 Distance len22 = 0; 1901 if (len1 > len2) { 1902 len11 = len1 / 2; 1903 advance(first_cut, len11); 1904 second_cut = lower_bound(middle, last, *first_cut); 1905 distance(middle, second_cut, len22); 1906 } 1907 else { 1908 len22 = len2 / 2; 1909 advance(second_cut, len22); 1910 first_cut = upper_bound(first, middle, *second_cut); 1911 distance(first, first_cut, len11); 1912 } 1913 rotate(first_cut, middle, second_cut); 1914 BidirectionalIterator new_middle = first_cut; 1915 advance(new_middle, len22); 1916 __merge_without_buffer(first, first_cut, new_middle, len11, len22); 1917 __merge_without_buffer(new_middle, second_cut, last, len1 - len11, 1918 len2 - len22); 1919 } 1920 1921 template <class BidirectionalIterator, class Distance, class Compare> 1922 void __merge_without_buffer(BidirectionalIterator first, 1923 BidirectionalIterator middle, 1924 BidirectionalIterator last, 1925 Distance len1, Distance len2, Compare comp) { 1926 if (len1 == 0 || len2 == 0) return; 1927 if (len1 + len2 == 2) { 1928 if (comp(*middle, *first)) iter_swap(first, middle); 1929 return; 1930 } 1931 BidirectionalIterator first_cut = first; 1932 BidirectionalIterator second_cut = middle; 1933 Distance len11 = 0; 1934 Distance len22 = 0; 1935 if (len1 > len2) { 1936 len11 = len1 / 2; 1937 advance(first_cut, len11); 1938 second_cut = lower_bound(middle, last, *first_cut, comp); 1939 distance(middle, second_cut, len22); 1940 } 1941 else { 1942 len22 = len2 / 2; 1943 advance(second_cut, len22); 1944 first_cut = upper_bound(first, middle, *second_cut, comp); 1945 distance(first, first_cut, len11); 1946 } 1947 rotate(first_cut, middle, second_cut); 1948 BidirectionalIterator new_middle = first_cut; 1949 advance(new_middle, len22); 1950 __merge_without_buffer(first, first_cut, new_middle, len11, len22, comp); 1951 __merge_without_buffer(new_middle, second_cut, last, len1 - len11, 1952 len2 - len22, comp); 1953 } 1954 1955 template <class BidirectionalIterator1, class BidirectionalIterator2, 1956 class Distance> 1957 BidirectionalIterator1 __rotate_adaptive(BidirectionalIterator1 first, 1958 BidirectionalIterator1 middle, 1959 BidirectionalIterator1 last, 1960 Distance len1, Distance len2, 1961 BidirectionalIterator2 buffer, 1962 Distance buffer_size) { 1963 BidirectionalIterator2 buffer_end; 1964 if (len1 > len2 && len2 <= buffer_size) { 1965 buffer_end = copy(middle, last, buffer); 1966 copy_backward(first, middle, last); 1967 return copy(buffer, buffer_end, first); 1968 } else if (len1 <= buffer_size) { 1969 buffer_end = copy(first, middle, buffer); 1970 copy(middle, last, first); 1971 return copy_backward(buffer, buffer_end, last); 1972 } else { 1973 rotate(first, middle, last); 1974 advance(first, len2); 1975 return first; 1976 } 1977 } 1978 1979 template <class BidirectionalIterator1, class BidirectionalIterator2, 1980 class BidirectionalIterator3> 1981 BidirectionalIterator3 __merge_backward(BidirectionalIterator1 first1, 1982 BidirectionalIterator1 last1, 1983 BidirectionalIterator2 first2, 1984 BidirectionalIterator2 last2, 1985 BidirectionalIterator3 result) { 1986 if (first1 == last1) return copy_backward(first2, last2, result); 1987 if (first2 == last2) return copy_backward(first1, last1, result); 1988 --last1; 1989 --last2; 1990 while (true) { 1991 if (*last2 < *last1) { 1992 *--result = *last1; 1993 if (first1 == last1) return copy_backward(first2, ++last2, result); 1994 --last1; 1995 } 1996 else { 1997 *--result = *last2; 1998 if (first2 == last2) return copy_backward(first1, ++last1, result); 1999 --last2; 2000 } 2001 } 2002 } 2003 2004 template <class BidirectionalIterator1, class BidirectionalIterator2, 2005 class BidirectionalIterator3, class Compare> 2006 BidirectionalIterator3 __merge_backward(BidirectionalIterator1 first1, 2007 BidirectionalIterator1 last1, 2008 BidirectionalIterator2 first2, 2009 BidirectionalIterator2 last2, 2010 BidirectionalIterator3 result, 2011 Compare comp) { 2012 if (first1 == last1) return copy_backward(first2, last2, result); 2013 if (first2 == last2) return copy_backward(first1, last1, result); 2014 --last1; 2015 --last2; 2016 while (true) { 2017 if (comp(*last2, *last1)) { 2018 *--result = *last1; 2019 if (first1 == last1) return copy_backward(first2, ++last2, result); 2020 --last1; 2021 } 2022 else { 2023 *--result = *last2; 2024 if (first2 == last2) return copy_backward(first1, ++last1, result); 2025 --last2; 2026 } 2027 } 2028 } 2029 2030 template <class BidirectionalIterator, class Distance, class Pointer> 2031 void __merge_adaptive(BidirectionalIterator first, 2032 BidirectionalIterator middle, 2033 BidirectionalIterator last, Distance len1, Distance len2, 2034 Pointer buffer, Distance buffer_size) { 2035 if (len1 <= len2 && len1 <= buffer_size) { 2036 Pointer end_buffer = copy(first, middle, buffer); 2037 merge(buffer, end_buffer, middle, last, first); 2038 } 2039 else if (len2 <= buffer_size) { 2040 Pointer end_buffer = copy(middle, last, buffer); 2041 __merge_backward(first, middle, buffer, end_buffer, last); 2042 } 2043 else { 2044 BidirectionalIterator first_cut = first; 2045 BidirectionalIterator second_cut = middle; 2046 Distance len11 = 0; 2047 Distance len22 = 0; 2048 if (len1 > len2) { 2049 len11 = len1 / 2; 2050 advance(first_cut, len11); 2051 second_cut = lower_bound(middle, last, *first_cut); 2052 distance(middle, second_cut, len22); 2053 } 2054 else { 2055 len22 = len2 / 2; 2056 advance(second_cut, len22); 2057 first_cut = upper_bound(first, middle, *second_cut); 2058 distance(first, first_cut, len11); 2059 } 2060 BidirectionalIterator new_middle = 2061 __rotate_adaptive(first_cut, middle, second_cut, len1 - len11, 2062 len22, buffer, buffer_size); 2063 __merge_adaptive(first, first_cut, new_middle, len11, len22, buffer, 2064 buffer_size); 2065 __merge_adaptive(new_middle, second_cut, last, len1 - len11, 2066 len2 - len22, buffer, buffer_size); 2067 } 2068 } 2069 2070 template <class BidirectionalIterator, class Distance, class Pointer, 2071 class Compare> 2072 void __merge_adaptive(BidirectionalIterator first, 2073 BidirectionalIterator middle, 2074 BidirectionalIterator last, Distance len1, Distance len2, 2075 Pointer buffer, Distance buffer_size, Compare comp) { 2076 if (len1 <= len2 && len1 <= buffer_size) { 2077 Pointer end_buffer = copy(first, middle, buffer); 2078 merge(buffer, end_buffer, middle, last, first, comp); 2079 } 2080 else if (len2 <= buffer_size) { 2081 Pointer end_buffer = copy(middle, last, buffer); 2082 __merge_backward(first, middle, buffer, end_buffer, last, comp); 2083 } 2084 else { 2085 BidirectionalIterator first_cut = first; 2086 BidirectionalIterator second_cut = middle; 2087 Distance len11 = 0; 2088 Distance len22 = 0; 2089 if (len1 > len2) { 2090 len11 = len1 / 2; 2091 advance(first_cut, len11); 2092 second_cut = lower_bound(middle, last, *first_cut, comp); 2093 distance(middle, second_cut, len22); 2094 } 2095 else { 2096 len22 = len2 / 2; 2097 advance(second_cut, len22); 2098 first_cut = upper_bound(first, middle, *second_cut, comp); 2099 distance(first, first_cut, len11); 2100 } 2101 BidirectionalIterator new_middle = 2102 __rotate_adaptive(first_cut, middle, second_cut, len1 - len11, 2103 len22, buffer, buffer_size); 2104 __merge_adaptive(first, first_cut, new_middle, len11, len22, buffer, 2105 buffer_size, comp); 2106 __merge_adaptive(new_middle, second_cut, last, len1 - len11, 2107 len2 - len22, buffer, buffer_size, comp); 2108 } 2109 } 2110 2111 template <class BidirectionalIterator, class T, class Distance> 2112 inline void __inplace_merge_aux(BidirectionalIterator first, 2113 BidirectionalIterator middle, 2114 BidirectionalIterator last, T*, Distance*) { 2115 Distance len1 = 0; 2116 distance(first, middle, len1); 2117 Distance len2 = 0; 2118 distance(middle, last, len2); 2119 2120 temporary_buffer<BidirectionalIterator, T> buf(first, last); 2121 if (buf.begin() == 0) 2122 __merge_without_buffer(first, middle, last, len1, len2); 2123 else 2124 __merge_adaptive(first, middle, last, len1, len2, 2125 buf.begin(), Distance(buf.size())); 2126 } 2127 2128 template <class BidirectionalIterator, class T, class Distance, class Compare> 2129 inline void __inplace_merge_aux(BidirectionalIterator first, 2130 BidirectionalIterator middle, 2131 BidirectionalIterator last, T*, Distance*, 2132 Compare comp) { 2133 Distance len1 = 0; 2134 distance(first, middle, len1); 2135 Distance len2 = 0; 2136 distance(middle, last, len2); 2137 2138 temporary_buffer<BidirectionalIterator, T> buf(first, last); 2139 if (buf.begin() == 0) 2140 __merge_without_buffer(first, middle, last, len1, len2, comp); 2141 else 2142 __merge_adaptive(first, middle, last, len1, len2, 2143 buf.begin(), Distance(buf.size()), 2144 comp); 2145 } 2146 2147 template <class BidirectionalIterator> 2148 inline void inplace_merge(BidirectionalIterator first, 2149 BidirectionalIterator middle, 2150 BidirectionalIterator last) { 2151 if (first == middle || middle == last) return; 2152 __inplace_merge_aux(first, middle, last, value_type(first), 2153 distance_type(first)); 2154 } 2155 2156 template <class BidirectionalIterator, class Compare> 2157 inline void inplace_merge(BidirectionalIterator first, 2158 BidirectionalIterator middle, 2159 BidirectionalIterator last, Compare comp) { 2160 if (first == middle || middle == last) return; 2161 __inplace_merge_aux(first, middle, last, value_type(first), 2162 distance_type(first), comp); 2163 } 2164 2165 // 判断[first2, last2)是否包含在[first1, last1)中, 2166 // 注意: 两个区间要保证有序, 如果容器是降序排列, 那么要使用另一个版本, 2167 // 并使用greater<>()来比较 2168 template <class InputIterator1, class InputIterator2> 2169 bool includes(InputIterator1 first1, InputIterator1 last1, 2170 InputIterator2 first2, InputIterator2 last2) 2171 { 2172 while (first1 != last1 && first2 != last2) 2173 if (*first2 < *first1) 2174 return false; 2175 else if(*first1 < *first2) 2176 ++first1; 2177 else 2178 ++first1, ++first2; 2179 2180 return first2 == last2; 2181 } 2182 2183 // 除了自己指定判别式, 其余同上 2184 template <class InputIterator1, class InputIterator2, class Compare> 2185 bool includes(InputIterator1 first1, InputIterator1 last1, 2186 InputIterator2 first2, InputIterator2 last2, Compare comp) 2187 { 2188 while (first1 != last1 && first2 != last2) 2189 if (comp(*first2, *first1)) 2190 return false; 2191 else if(comp(*first1, *first2)) 2192 ++first1; 2193 else 2194 ++first1, ++first2; 2195 2196 return first2 == last2; 2197 } 2198 2199 //// 2200 // 四个集合相关算法 2201 //// 2202 2203 // 求两个集合的的并集, 和数学定义的并集有一些不一样 2204 // 对于两个集合S1[first1, last1)和S2[first2, last2) 2205 // 假设其中k元素在S1中出现n1次, 在S2中出现n2次 2206 // 那么求出的并集选取max(n1, n2)为并集内k元素个数 2207 // 注意: 集合相关操作均要求区间有序, 后面不再强调 2208 template <class InputIterator1, class InputIterator2, class OutputIterator> 2209 OutputIterator set_union(InputIterator1 first1, InputIterator1 last1, 2210 InputIterator2 first2, InputIterator2 last2, 2211 OutputIterator result) 2212 { 2213 // 先进行历遍操作 2214 while (first1 != last1 && first2 != last2) { 2215 // 这里把现在能确定的并集先加入到result中 2216 // 先把较小的加入到结果中, 否则如果相等, 那么也要加入 2217 if (*first1 < *first2) { 2218 *result = *first1; 2219 ++first1; 2220 } 2221 else if (*first2 < *first1) { 2222 *result = *first2; 2223 ++first2; 2224 } 2225 else { 2226 *result = *first1; 2227 ++first1; 2228 ++first2; 2229 } 2230 ++result; 2231 } 2232 2233 // 将剩余的元素加入到并集中 2234 return copy(first2, last2, copy(first1, last1, result)); 2235 } 2236 2237 // 使用用户指定的二元比较判别式, 其余同上面 2238 template <class InputIterator1, class InputIterator2, class OutputIterator, 2239 class Compare> 2240 OutputIterator set_union(InputIterator1 first1, InputIterator1 last1, 2241 InputIterator2 first2, InputIterator2 last2, 2242 OutputIterator result, Compare comp) 2243 { 2244 while (first1 != last1 && first2 != last2) { 2245 if (comp(*first1, *first2)) { 2246 *result = *first1; 2247 ++first1; 2248 } 2249 else if (comp(*first2, *first1)) { 2250 *result = *first2; 2251 ++first2; 2252 } 2253 else { 2254 *result = *first1; 2255 ++first1; 2256 ++first2; 2257 } 2258 ++result; 2259 } 2260 return copy(first2, last2, copy(first1, last1, result)); 2261 } 2262 2263 // 求两个集合的的交集, 和数学定义的并集有一些不一样 2264 // 对于两个集合S1[first1, last1)和S2[first2, last2) 2265 // 假设其中k元素在S1中出现n1次, 在S2中出现n2次 2266 // 那么求出的交集选取min(n1, n2)为交集内k元素个数 2267 template <class InputIterator1, class InputIterator2, class OutputIterator> 2268 OutputIterator set_intersection(InputIterator1 first1, InputIterator1 last1, 2269 InputIterator2 first2, InputIterator2 last2, 2270 OutputIterator result) 2271 { 2272 // 算法很简单, 不进行说明 2273 while (first1 != last1 && first2 != last2) 2274 if (*first1 < *first2) 2275 ++first1; 2276 else if (*first2 < *first1) 2277 ++first2; 2278 else { 2279 *result = *first1; 2280 ++first1; 2281 ++first2; 2282 ++result; 2283 } 2284 return result; 2285 } 2286 2287 // 使用用户指定的二元比较判别式, 其余同上面 2288 template <class InputIterator1, class InputIterator2, class OutputIterator, 2289 class Compare> 2290 OutputIterator set_intersection(InputIterator1 first1, InputIterator1 last1, 2291 InputIterator2 first2, InputIterator2 last2, 2292 OutputIterator result, Compare comp) 2293 { 2294 while (first1 != last1 && first2 != last2) 2295 if (comp(*first1, *first2)) 2296 ++first1; 2297 else if (comp(*first2, *first1)) 2298 ++first2; 2299 else { 2300 *result = *first1; 2301 ++first1; 2302 ++first2; 2303 ++result; 2304 } 2305 return result; 2306 } 2307 2308 // 求两个集合的的差集, 和数学定义的并集有一些不一样 2309 // 对于两个集合S1[first1, last1)和S2[first2, last2) 2310 // 假设其中k元素在S1中出现n1次, 在S2中出现n2次 2311 // 那么求出的差集选取max(n1 - n2, 0)为差集内k元素个数 2312 template <class InputIterator1, class InputIterator2, class OutputIterator> 2313 OutputIterator set_difference(InputIterator1 first1, InputIterator1 last1, 2314 InputIterator2 first2, InputIterator2 last2, 2315 OutputIterator result) 2316 { 2317 while (first1 != last1 && first2 != last2) 2318 if (*first1 < *first2) { // 找到了一个合适的元素, 加入到结果中 2319 *result = *first1; // 向后调整迭代器 2320 ++first1; 2321 ++result; 2322 } 2323 else if (*first2 < *first1) // 元素不合适, 调整迭代器 2324 ++first2; 2325 else { // 这个用来处理出现相同元素的情况 2326 ++first1; 2327 ++first2; 2328 } 2329 2330 // 将剩余的元素加入到结果中 2331 return copy(first1, last1, result); 2332 } 2333 2334 // 使用用户指定的二元比较判别式, 其余同上面 2335 template <class InputIterator1, class InputIterator2, class OutputIterator, 2336 class Compare> 2337 OutputIterator set_difference(InputIterator1 first1, InputIterator1 last1, 2338 InputIterator2 first2, InputIterator2 last2, 2339 OutputIterator result, Compare comp) { 2340 while (first1 != last1 && first2 != last2) 2341 if (comp(*first1, *first2)) { 2342 *result = *first1; 2343 ++first1; 2344 ++result; 2345 } 2346 else if (comp(*first2, *first1)) 2347 ++first2; 2348 else { 2349 ++first1; 2350 ++first2; 2351 } 2352 return copy(first1, last1, result); 2353 } 2354 2355 // 求两个集合的的对称差集, 和数学定义的并集有一些不一样 2356 // 其用公式可以表示为(S1 - S2) U (S2 - S1) 2357 // 对于两个集合S1[first1, last1)和S2[first2, last2) 2358 // 假设其中k元素在S1中出现n1次, 在S2中出现n2次 2359 // 那么结果中会出现|n1 - n2|个k元素 2360 template <class InputIterator1, class InputIterator2, class OutputIterator> 2361 OutputIterator set_symmetric_difference(InputIterator1 first1, 2362 InputIterator1 last1, 2363 InputIterator2 first2, 2364 InputIterator2 last2, 2365 OutputIterator result) 2366 { 2367 // 算法和上面的差不多, 不解释 2368 while (first1 != last1 && first2 != last2) 2369 if (*first1 < *first2) { 2370 *result = *first1; 2371 ++first1; 2372 ++result; 2373 } 2374 else if (*first2 < *first1) { 2375 *result = *first2; 2376 ++first2; 2377 ++result; 2378 } 2379 else { 2380 ++first1; 2381 ++first2; 2382 } 2383 2384 return copy(first2, last2, copy(first1, last1, result)); 2385 } 2386 2387 // 使用用户指定的二元比较判别式, 其余同上面 2388 template <class InputIterator1, class InputIterator2, class OutputIterator, 2389 class Compare> 2390 OutputIterator set_symmetric_difference(InputIterator1 first1, 2391 InputIterator1 last1, 2392 InputIterator2 first2, 2393 InputIterator2 last2, 2394 OutputIterator result, Compare comp) 2395 { 2396 while (first1 != last1 && first2 != last2) 2397 if (comp(*first1, *first2)) { 2398 *result = *first1; 2399 ++first1; 2400 ++result; 2401 } 2402 else if (comp(*first2, *first1)) { 2403 *result = *first2; 2404 ++first2; 2405 ++result; 2406 } 2407 else { 2408 ++first1; 2409 ++first2; 2410 } 2411 return copy(first2, last2, copy(first1, last1, result)); 2412 } 2413 2414 // 查找指定区间内最大的元素 2415 template <class ForwardIterator> 2416 ForwardIterator max_element(ForwardIterator first, ForwardIterator last) 2417 { 2418 if (first == last) return first; 2419 ForwardIterator result = first; 2420 while (++first != last) 2421 if (*result < *first) result = first; 2422 return result; 2423 } 2424 2425 // 使用用户指定的二元比较判别式, 其余同上面 2426 template <class ForwardIterator, class Compare> 2427 ForwardIterator max_element(ForwardIterator first, ForwardIterator last, 2428 Compare comp) 2429 { 2430 if (first == last) return first; 2431 ForwardIterator result = first; 2432 while (++first != last) 2433 if (comp(*result, *first)) result = first; 2434 return result; 2435 } 2436 2437 // 查找指定区间内最小的元素 2438 template <class ForwardIterator> 2439 ForwardIterator min_element(ForwardIterator first, ForwardIterator last) 2440 { 2441 if (first == last) return first; 2442 ForwardIterator result = first; 2443 while (++first != last) 2444 if (*first < *result) result = first; 2445 return result; 2446 } 2447 2448 template <class ForwardIterator, class Compare> 2449 ForwardIterator min_element(ForwardIterator first, ForwardIterator last, 2450 Compare comp) 2451 { 2452 if (first == last) return first; 2453 ForwardIterator result = first; 2454 while (++first != last) 2455 if (comp(*first, *result)) result = first; 2456 return result; 2457 } 2458 2459 // 获取下一个全排列 2460 template <class BidirectionalIterator> 2461 bool next_permutation(BidirectionalIterator first, 2462 BidirectionalIterator last) 2463 { 2464 if (first == last) return false; 2465 BidirectionalIterator i = first; 2466 ++i; 2467 if (i == last) return false; 2468 i = last; 2469 --i; 2470 2471 for(;;) { 2472 BidirectionalIterator ii = i; 2473 --i; 2474 if (*i < *ii) { 2475 BidirectionalIterator j = last; 2476 while (!(*i < *--j)); 2477 iter_swap(i, j); 2478 reverse(ii, last); 2479 return true; 2480 } 2481 if (i == first) { 2482 reverse(first, last); 2483 return false; 2484 } 2485 } 2486 } 2487 2488 template <class BidirectionalIterator, class Compare> 2489 bool next_permutation(BidirectionalIterator first, BidirectionalIterator last, 2490 Compare comp) { 2491 if (first == last) return false; 2492 BidirectionalIterator i = first; 2493 ++i; 2494 if (i == last) return false; 2495 i = last; 2496 --i; 2497 2498 for(;;) { 2499 BidirectionalIterator ii = i; 2500 --i; 2501 if (comp(*i, *ii)) { 2502 BidirectionalIterator j = last; 2503 while (!comp(*i, *--j)); 2504 iter_swap(i, j); 2505 reverse(ii, last); 2506 return true; 2507 } 2508 if (i == first) { 2509 reverse(first, last); 2510 return false; 2511 } 2512 } 2513 } 2514 2515 template <class BidirectionalIterator> 2516 bool prev_permutation(BidirectionalIterator first, 2517 BidirectionalIterator last) { 2518 if (first == last) return false; 2519 BidirectionalIterator i = first; 2520 ++i; 2521 if (i == last) return false; 2522 i = last; 2523 --i; 2524 2525 for(;;) { 2526 BidirectionalIterator ii = i; 2527 --i; 2528 if (*ii < *i) { 2529 BidirectionalIterator j = last; 2530 while (!(*--j < *i)); 2531 iter_swap(i, j); 2532 reverse(ii, last); 2533 return true; 2534 } 2535 if (i == first) { 2536 reverse(first, last); 2537 return false; 2538 } 2539 } 2540 } 2541 2542 // 获取前一个全排列 2543 template <class BidirectionalIterator, class Compare> 2544 bool prev_permutation(BidirectionalIterator first, BidirectionalIterator last, 2545 Compare comp) { 2546 if (first == last) return false; 2547 BidirectionalIterator i = first; 2548 ++i; 2549 if (i == last) return false; 2550 i = last; 2551 --i; 2552 2553 for(;;) { 2554 BidirectionalIterator ii = i; 2555 --i; 2556 if (comp(*ii, *i)) { 2557 BidirectionalIterator j = last; 2558 while (!comp(*--j, *i)); 2559 iter_swap(i, j); 2560 reverse(ii, last); 2561 return true; 2562 } 2563 if (i == first) { 2564 reverse(first, last); 2565 return false; 2566 } 2567 } 2568 } 2569 2570 // 在区间[first1, last1)内查找区间[first2, last2)第一次出现的位置 2571 template <class InputIterator, class ForwardIterator> 2572 InputIterator find_first_of(InputIterator first1, InputIterator last1, 2573 ForwardIterator first2, ForwardIterator last2) 2574 { 2575 for ( ; first1 != last1; ++first1) 2576 for (ForwardIterator iter = first2; iter != last2; ++iter) 2577 if (*first1 == *iter) 2578 return first1; 2579 return last1; 2580 } 2581 2582 // 使用用户指定的判别式, 其余同上面 2583 template <class InputIterator, class ForwardIterator, class BinaryPredicate> 2584 InputIterator find_first_of(InputIterator first1, InputIterator last1, 2585 ForwardIterator first2, ForwardIterator last2, 2586 BinaryPredicate comp) 2587 { 2588 for ( ; first1 != last1; ++first1) 2589 for (ForwardIterator iter = first2; iter != last2; ++iter) 2590 if (comp(*first1, *iter)) 2591 return first1; 2592 return last1; 2593 } 2594 2595 2596 // Search [first2, last2) as a subsequence in [first1, last1). 2597 2598 // find_end for forward iterators. 2599 template <class ForwardIterator1, class ForwardIterator2> 2600 ForwardIterator1 __find_end(ForwardIterator1 first1, ForwardIterator1 last1, 2601 ForwardIterator2 first2, ForwardIterator2 last2, 2602 forward_iterator_tag, forward_iterator_tag) 2603 { 2604 if (first2 == last2) // 如果查找的目标区间为空, 那么就返回last1 2605 return last1; 2606 else { 2607 ForwardIterator1 result = last1; 2608 while (1) { 2609 // 查找匹配区间 2610 ForwardIterator1 new_result = search(first1, last1, first2, last2); 2611 if (new_result == last1) // 没找到 2612 return result; 2613 else { // 找到了, 准备看后面还有没有匹配区间 2614 result = new_result; 2615 first1 = new_result; 2616 ++first1; 2617 } 2618 } 2619 } 2620 } 2621 2622 template <class ForwardIterator1, class ForwardIterator2, 2623 class BinaryPredicate> 2624 ForwardIterator1 __find_end(ForwardIterator1 first1, ForwardIterator1 last1, 2625 ForwardIterator2 first2, ForwardIterator2 last2, 2626 forward_iterator_tag, forward_iterator_tag, 2627 BinaryPredicate comp) 2628 { 2629 if (first2 == last2) 2630 return last1; 2631 else { 2632 ForwardIterator1 result = last1; 2633 while (1) { 2634 ForwardIterator1 new_result = search(first1, last1, first2, last2, comp); 2635 if (new_result == last1) 2636 return result; 2637 else { 2638 result = new_result; 2639 first1 = new_result; 2640 ++first1; 2641 } 2642 } 2643 } 2644 } 2645 2646 // find_end for bidirectional iterators. Requires partial specialization. 2647 #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION 2648 2649 template <class BidirectionalIterator1, class BidirectionalIterator2> 2650 BidirectionalIterator1 2651 __find_end(BidirectionalIterator1 first1, BidirectionalIterator1 last1, 2652 BidirectionalIterator2 first2, BidirectionalIterator2 last2, 2653 bidirectional_iterator_tag, bidirectional_iterator_tag) 2654 { 2655 typedef reverse_iterator<BidirectionalIterator1> reviter1; 2656 typedef reverse_iterator<BidirectionalIterator2> reviter2; 2657 2658 reviter1 rlast1(first1); 2659 reviter2 rlast2(first2); 2660 reviter1 rresult = search(reviter1(last1), rlast1, reviter2(last2), rlast2); 2661 2662 if (rresult == rlast1) 2663 return last1; 2664 else { 2665 BidirectionalIterator1 result = rresult.base(); 2666 advance(result, -distance(first2, last2)); 2667 return result; 2668 } 2669 } 2670 2671 // 可以逆向查找, 速度块 2672 template <class BidirectionalIterator1, class BidirectionalIterator2, 2673 class BinaryPredicate> 2674 BidirectionalIterator1 2675 __find_end(BidirectionalIterator1 first1, BidirectionalIterator1 last1, 2676 BidirectionalIterator2 first2, BidirectionalIterator2 last2, 2677 bidirectional_iterator_tag, bidirectional_iterator_tag, 2678 BinaryPredicate comp) 2679 { 2680 typedef reverse_iterator<BidirectionalIterator1> reviter1; 2681 typedef reverse_iterator<BidirectionalIterator2> reviter2; 2682 2683 reviter1 rlast1(first1); 2684 reviter2 rlast2(first2); 2685 reviter1 rresult = search(reviter1(last1), rlast1, reviter2(last2), rlast2, 2686 comp); 2687 2688 if (rresult == rlast1) 2689 return last1; 2690 else { 2691 BidirectionalIterator1 result = rresult.base(); 2692 advance(result, -distance(first2, last2)); 2693 return result; 2694 } 2695 } 2696 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 2697 2698 // 在区间[first1, last1)内查找区间[first2, last2)最后一次出现的位置 2699 template <class ForwardIterator1, class ForwardIterator2> 2700 inline ForwardIterator1 2701 find_end(ForwardIterator1 first1, ForwardIterator1 last1, 2702 ForwardIterator2 first2, ForwardIterator2 last2) 2703 { 2704 // 这里根据是否能逆向查找来派发函数 2705 #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION 2706 typedef typename iterator_traits<ForwardIterator1>::iterator_category 2707 category1; 2708 typedef typename iterator_traits<ForwardIterator2>::iterator_category 2709 category2; 2710 return __find_end(first1, last1, first2, last2, category1(), category2()); 2711 #else /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 2712 return __find_end(first1, last1, first2, last2, 2713 forward_iterator_tag(), forward_iterator_tag()); 2714 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 2715 } 2716 2717 // 使用用户指定的判别式, 其余同上面 2718 template <class ForwardIterator1, class ForwardIterator2, 2719 class BinaryPredicate> 2720 inline ForwardIterator1 2721 find_end(ForwardIterator1 first1, ForwardIterator1 last1, 2722 ForwardIterator2 first2, ForwardIterator2 last2, 2723 BinaryPredicate comp) 2724 { 2725 #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION 2726 typedef typename iterator_traits<ForwardIterator1>::iterator_category 2727 category1; 2728 typedef typename iterator_traits<ForwardIterator2>::iterator_category 2729 category2; 2730 return __find_end(first1, last1, first2, last2, category1(), category2(), 2731 comp); 2732 #else /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 2733 return __find_end(first1, last1, first2, last2, 2734 forward_iterator_tag(), forward_iterator_tag(), 2735 comp); 2736 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */ 2737 } 2738 2739 template <class RandomAccessIterator, class Distance> 2740 bool __is_heap(RandomAccessIterator first, RandomAccessIterator last, 2741 Distance*) 2742 { 2743 const Distance n = last - first; 2744 2745 Distance parent = 0; 2746 for (Distance child = 1; child < n; ++child) { 2747 if (first[parent] < first[child]) 2748 return false; 2749 if ((child & 1) == 0) 2750 ++parent; 2751 } 2752 return true; 2753 } 2754 2755 template <class RandomAccessIterator> 2756 inline bool is_heap(RandomAccessIterator first, RandomAccessIterator last) 2757 { 2758 return __is_heap(first, last, distance_type(first)); 2759 } 2760 2761 2762 template <class RandomAccessIterator, class Distance, class StrictWeakOrdering> 2763 bool __is_heap(RandomAccessIterator first, RandomAccessIterator last, 2764 StrictWeakOrdering comp, 2765 Distance*) 2766 { 2767 const Distance n = last - first; 2768 2769 Distance parent = 0; 2770 for (Distance child = 1; child < n; ++child) { 2771 if (comp(first[parent], first[child])) 2772 return false; 2773 if ((child & 1) == 0) 2774 ++parent; 2775 } 2776 return true; 2777 } 2778 2779 template <class RandomAccessIterator, class StrictWeakOrdering> 2780 inline bool is_heap(RandomAccessIterator first, RandomAccessIterator last, 2781 StrictWeakOrdering comp) 2782 { 2783 return __is_heap(first, last, comp, distance_type(first)); 2784 } 2785 2786 2787 template <class ForwardIterator> 2788 bool is_sorted(ForwardIterator first, ForwardIterator last) 2789 { 2790 if (first == last) 2791 return true; 2792 2793 ForwardIterator next = first; 2794 for (++next; next != last; first = next, ++next) { 2795 if (*next < *first) 2796 return false; 2797 } 2798 2799 return true; 2800 } 2801 2802 template <class ForwardIterator, class StrictWeakOrdering> 2803 bool is_sorted(ForwardIterator first, ForwardIterator last, 2804 StrictWeakOrdering comp) 2805 { 2806 if (first == last) 2807 return true; 2808 2809 ForwardIterator next = first; 2810 for (++next; next != last; first = next, ++next) { 2811 if (comp(*next, *first)) 2812 return false; 2813 } 2814 2815 return true; 2816 } 2817 2818 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32) 2819 #pragma reset woff 1209 2820 #endif 2821 2822 __STL_END_NAMESPACE 2823 2824 #endif /* __SGI_STL_INTERNAL_ALGO_H */ 2825 2826 // Local Variables: 2827 // mode:C++ 2828 // End: