00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00073 #ifndef RANGELIB_INCL_RANGELIB_HPP_ALGORITHMS
00074 #define RANGELIB_INCL_RANGELIB_HPP_ALGORITHMS
00075
00076 #ifndef STLSOFT_DOCUMENTATION_SKIP_SECTION
00077 # define RANGELIB_VER_RANGELIB_HPP_ALGORITHMS_MAJOR 2
00078 # define RANGELIB_VER_RANGELIB_HPP_ALGORITHMS_MINOR 3
00079 # define RANGELIB_VER_RANGELIB_HPP_ALGORITHMS_REVISION 5
00080 # define RANGELIB_VER_RANGELIB_HPP_ALGORITHMS_EDIT 45
00081 #endif
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098 #ifndef RANGELIB_INCL_RANGELIB_HPP_RANGELIB
00099 # include <rangelib/rangelib.hpp>
00100 #endif
00101 #ifndef RANGELIB_INCL_RANGELIB_HPP_RANGE_CATEGORIES
00102 # include <rangelib/range_categories.hpp>
00103 #endif
00104 #ifndef RANGELIB_INCL_RANGELIB_ERROR_HPP_EXCEPTIONS
00105 # include <rangelib/error/exceptions.hpp>
00106 #endif
00107 #ifndef RANGELIB_INCL_RANGELIB_HPP_BASIC_INDIRECT_RANGE_ADAPTOR
00108 # include <rangelib/basic_indirect_range_adaptor.hpp>
00109 #endif
00110
00111 #ifndef STLSOFT_INCL_ALGORITHM
00112 # define STLSOFT_INCL_ALGORITHM
00113 # include <algorithm>
00114 #endif
00115 #ifndef STLSOFT_INCL_NUMERIC
00116 # define STLSOFT_INCL_NUMERIC
00117 # include <numeric>
00118 #endif
00119
00120 #ifdef STLSOFT_UNITTEST
00121 # include <rangelib/integral_range.hpp>
00122 # include <rangelib/sequence_range.hpp>
00123 # include <iterator>
00124 # include <list>
00125 #endif
00126
00127
00128
00129
00130
00131 #ifndef RANGELIB_NO_NAMESPACE
00132 # if defined(_STLSOFT_NO_NAMESPACE) || \
00133 defined(STLSOFT_DOCUMENTATION_SKIP_SECTION)
00134
00135 namespace rangelib
00136 {
00137 # else
00138
00139
00140 namespace stlsoft
00141 {
00142
00143 namespace rangelib_project
00144 {
00145
00146 # endif
00147 #endif
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157 template< ss_typename_param_k R
00158 , ss_typename_param_k T
00159 >
00160 inline T r_accumulate_2_impl(R r, T val, notional_range_tag const&)
00161 {
00162 for(; r; ++r)
00163 {
00164 val = val + *r;
00165 }
00166
00167 return val;
00168 }
00169
00170 template< ss_typename_param_k R
00171 , ss_typename_param_k T
00172 >
00173 inline T r_accumulate_2_impl(R r, T val, iterable_range_tag const&)
00174 {
00175 return std::accumulate(r.begin(), r.end(), val);
00176 }
00177
00178 template< ss_typename_param_k R
00179 , ss_typename_param_k T
00180 >
00181 inline T r_accumulate_2_impl(R r, T val, basic_indirect_range_tag const&)
00182 {
00183 return indirect_range_adaptor<R>(r).accumulate(val);
00184 }
00185
00186 template< ss_typename_param_k R
00187 , ss_typename_param_k T
00188 >
00189 inline T r_accumulate_2_impl(R r, T val, indirect_range_tag const&)
00190 {
00191 return r.accumulate(val);
00192 }
00193
00204 template< ss_typename_param_k R
00205 , ss_typename_param_k T
00206 >
00207 inline T r_accumulate(R r, T val)
00208 {
00209 return r_accumulate_2_impl(r, val, r);
00210 }
00211
00212
00213
00214
00215
00216 template< ss_typename_param_k R
00217 , ss_typename_param_k T
00218 , ss_typename_param_k P
00219 >
00220 inline T r_accumulate_3_impl(R r, T val, P pred, notional_range_tag const&)
00221 {
00222 for(; r; ++r)
00223 {
00224 val = pred(val, *r);
00225 }
00226
00227 return val;
00228 }
00229
00230 template< ss_typename_param_k R
00231 , ss_typename_param_k T
00232 , ss_typename_param_k P
00233 >
00234 inline T r_accumulate_3_impl(R r, T val, P pred, iterable_range_tag const&)
00235 {
00236 return std::accumulate(r.begin(), r.end(), val, pred);
00237 }
00238
00239 template< ss_typename_param_k R
00240 , ss_typename_param_k T
00241 , ss_typename_param_k P
00242 >
00243 inline T r_accumulate_2_impl(R r, T val, P pred, basic_indirect_range_tag const&)
00244 {
00245 return indirect_range_adaptor<R>(r).accumulate(val, pred);
00246 }
00247
00248 template< ss_typename_param_k R
00249 , ss_typename_param_k T
00250 , ss_typename_param_k P
00251 >
00252 inline T r_accumulate_3_impl(R r, T val, P pred, indirect_range_tag const&)
00253 {
00254 return r.accumulate(val, pred);
00255 }
00256
00268 template< ss_typename_param_k R
00269 , ss_typename_param_k T
00270 , ss_typename_param_k P
00271 >
00272 inline T r_accumulate(R r, T val, P pred)
00273 {
00274 return r_accumulate_3_impl(r, val, pred, r);
00275 }
00276
00277
00278
00279
00280
00281
00282 template< ss_typename_param_k R
00283 , ss_typename_param_k O
00284 >
00285 inline O r_copy_impl(R r, O o, notional_range_tag const&)
00286 {
00287 for(; r; ++r, ++o)
00288 {
00289 *o = *r;
00290 }
00291
00292 return o;
00293 }
00294
00295 template< ss_typename_param_k R
00296 , ss_typename_param_k O
00297 >
00298 inline O r_copy_impl(R r, O o, iterable_range_tag const&)
00299 {
00300 return std::copy(r.begin(), r.end(), o);
00301 }
00302
00303 template< ss_typename_param_k R
00304 , ss_typename_param_k O
00305 >
00306 inline O r_copy_impl(R r, O o, indirect_range_tag const&)
00307 {
00308 return r.copy(o);
00309 }
00310
00311 template< ss_typename_param_k R
00312 , ss_typename_param_k O
00313 >
00314 inline O r_copy_impl(R r, O o, basic_indirect_range_tag const&)
00315 {
00316 return indirect_range_adaptor<R>(r).copy(o);
00317 }
00318
00328 template< ss_typename_param_k R
00329 , ss_typename_param_k O
00330 >
00331 inline O r_copy(R r, O o)
00332 {
00333 return r_copy_impl(r, o, r);
00334 }
00335
00336
00337
00338
00339
00340
00341 template< ss_typename_param_k R
00342 , ss_typename_param_k O
00343 , ss_typename_param_k P
00344 >
00345 inline O r_copy_if_impl(R r, O o, P pred, notional_range_tag const&)
00346 {
00347 for(; r; ++r)
00348 {
00349 if(pred(*r))
00350 {
00351 *o = *r;
00352
00353 ++o;
00354 }
00355 }
00356
00357 return o;
00358 }
00359
00360 #if 0
00361 template< ss_typename_param_k R
00362 , ss_typename_param_k O
00363 , ss_typename_param_k P
00364 >
00365 inline O r_copy_if_impl(R r, O o, P pred, iterable_range_tag const&)
00366 {
00367 return std::copy_if(r.begin(), r.end(), o);
00368 }
00369 #endif
00370
00371 template< ss_typename_param_k R
00372 , ss_typename_param_k O
00373 , ss_typename_param_k P
00374 >
00375 inline O r_copy_if_impl(R r, O o, P pred, indirect_range_tag const&)
00376 {
00377 return r.copy_if(o);
00378 }
00379
00380 template< ss_typename_param_k R
00381 , ss_typename_param_k O
00382 , ss_typename_param_k P
00383 >
00384 inline O r_copy_if_impl(R r, O o, P pred, basic_indirect_range_tag const&)
00385 {
00386 return indirect_range_adaptor<R>(r).copy_if(o);
00387 }
00388
00399 template< ss_typename_param_k R
00400 , ss_typename_param_k O
00401 , ss_typename_param_k P
00402 >
00403 inline O r_copy_if(R r, O o, P pred)
00404 {
00405 return r_copy_if_impl(r, o, pred, r);
00406 }
00407
00408
00409
00410
00411
00412
00413 template< ss_typename_param_k R
00414 , ss_typename_param_k T
00415 >
00416 inline ss_size_t r_count_impl(R r, T const& val, notional_range_tag const&)
00417 {
00418 ss_size_t n;
00419
00420 for(n = 0; r; ++r)
00421 {
00422 if(val == *r)
00423 {
00424 ++n;
00425 }
00426 }
00427
00428 return n;
00429 }
00430
00431 template< ss_typename_param_k R
00432 , ss_typename_param_k T
00433 >
00434 inline ss_size_t r_count_impl(R r, T const& val, iterable_range_tag const&)
00435 {
00436 return std::count(r.begin(), r.end(), val);
00437 }
00438
00439 template< ss_typename_param_k R
00440 , ss_typename_param_k T
00441 >
00442 inline ss_size_t r_count_impl(R r, T const& val, basic_indirect_range_tag const&)
00443 {
00444 return indirect_range_adaptor<R>(r).count(val);
00445 }
00446
00447 template< ss_typename_param_k R
00448 , ss_typename_param_k T
00449 >
00450 inline ss_size_t r_count_impl(R r, T const& val, indirect_range_tag const&)
00451 {
00452 return r.count(val);
00453 }
00454
00465 template< ss_typename_param_k R
00466 , ss_typename_param_k T
00467 >
00468 inline ss_size_t r_count(R r, T const& val)
00469 {
00470 return r_count_impl(r, val, r);
00471 }
00472
00473
00474
00475
00476
00477
00478 template< ss_typename_param_k R
00479 , ss_typename_param_k P
00480 >
00481 inline ss_size_t r_count_if_impl(R r, P pred, notional_range_tag const&)
00482 {
00483 ss_size_t n;
00484
00485 for(n = 0; r; ++r)
00486 {
00487 if(pred(*r))
00488 {
00489 ++n;
00490 }
00491 }
00492
00493 return n;
00494 }
00495
00496 template< ss_typename_param_k R
00497 , ss_typename_param_k P
00498 >
00499 inline ss_size_t r_count_if_impl(R r, P pred, iterable_range_tag const&)
00500 {
00501 return std::count_if(r.begin(), r.end(), pred);
00502 }
00503
00504 template< ss_typename_param_k R
00505 , ss_typename_param_k P
00506 >
00507 inline ss_size_t r_count_if_impl(R r, P pred, basic_indirect_range_tag const&)
00508 {
00509 return indirect_range_adaptor<R>(r).count_if(pred);
00510 }
00511
00512 template< ss_typename_param_k R
00513 , ss_typename_param_k P
00514 >
00515 inline ss_size_t r_count_if_impl(R r, P pred, indirect_range_tag const&)
00516 {
00517 return r.count_if(pred);
00518 }
00519
00530 template< ss_typename_param_k R
00531 , ss_typename_param_k P
00532 >
00533 inline ss_size_t r_count_if(R r, P pred)
00534 {
00535 return r_count_if_impl(r, pred, r);
00536 }
00537
00538
00539
00540
00541
00542
00543 template <ss_typename_param_k R>
00544 inline ss_ptrdiff_t r_distance_1_impl(R r, notional_range_tag const&)
00545 {
00546 ss_ptrdiff_t d = 0;
00547
00548 for(; r; ++r, ++d)
00549 {}
00550
00551 return d;
00552 }
00553
00554 template <ss_typename_param_k R>
00555 inline ss_ptrdiff_t r_distance_1_impl(R r, iterable_range_tag const&)
00556 {
00557 return std::distance(r.begin(), r.end());
00558 }
00559
00560 template <ss_typename_param_k R>
00561 inline ss_ptrdiff_t r_distance_1_impl(R r, indirect_range_tag const&)
00562 {
00563 return r.distance();
00564 }
00565
00566 template <ss_typename_param_k R>
00567 inline ss_ptrdiff_t r_distance_1_impl(R r, basic_indirect_range_tag const&)
00568 {
00569 return indirect_range_adaptor<R>(r).distance();
00570 }
00571
00581 template <ss_typename_param_k R>
00582 inline ss_ptrdiff_t r_distance(R r)
00583 {
00584 return r_distance_1_impl(r, r);
00585 }
00586
00587
00588
00589
00590
00591 template< ss_typename_param_k R1
00592 , ss_typename_param_k R2
00593 >
00594 inline ss_bool_t r_equal_1_impl(R1 r1, R2 r2, notional_range_tag const&, notional_range_tag const&)
00595 {
00596 for(; r1 && r2; ++r1, ++r2)
00597 {
00598 if(*r1 != *r2)
00599 {
00600 return false;
00601 }
00602 }
00603
00604 return true;
00605 }
00606
00607 template< ss_typename_param_k R1
00608 , ss_typename_param_k R2
00609 >
00610 inline ss_bool_t r_equal_1_impl(R1 r1, R2 r2, iterable_range_tag const&, iterable_range_tag const&)
00611 {
00612 return std::equal(r1.begin(), r1.end(), r2.begin());
00613 }
00614
00627 template< ss_typename_param_k R1
00628 , ss_typename_param_k R2
00629 >
00630 inline ss_bool_t r_equal(R1 r1, R2 r2)
00631 {
00632 if(r_distance(r1) > r_distance(r2))
00633 {
00634 return false;
00635 }
00636
00637 return r_equal_1_impl(r1, r2, r1, r2);
00638 }
00639
00640
00641
00642
00643
00644 template< ss_typename_param_k R1
00645 , ss_typename_param_k R2
00646 , ss_typename_param_k P
00647 >
00648 inline ss_bool_t r_equal_1_impl(R1 r1, R2 r2, P pred, notional_range_tag const&, notional_range_tag const&)
00649 {
00650 for(; r1 && r2; ++r1, ++r2)
00651 {
00652 if(!pred(*r1, *r2))
00653 {
00654 return false;
00655 }
00656 }
00657
00658 return true;
00659 }
00660
00661 template< ss_typename_param_k R1
00662 , ss_typename_param_k R2
00663 , ss_typename_param_k P
00664 >
00665 inline ss_bool_t r_equal_1_impl(R1 r1, R2 r2, P pred, iterable_range_tag const&, iterable_range_tag const&)
00666 {
00667 return std::equal(r1.begin(), r1.end(), r2.begin(), pred);
00668 }
00669
00681 template< ss_typename_param_k R1
00682 , ss_typename_param_k R2
00683 , ss_typename_param_k P
00684 >
00685 inline ss_bool_t r_equal(R1 r1, R2 r2, P pred)
00686 {
00687 STLSOFT_ASSERT(r_distance(r1) <= r_distance(r2));
00688
00689 return r_equal_1_impl(r1, r2, pred, r1, r2);
00690 }
00691
00692
00693
00694
00695
00696 template< ss_typename_param_k R
00697 , ss_typename_param_k T
00698 >
00699 inline ss_bool_t r_exists_impl(R r, T const& val, notional_range_tag const&)
00700 {
00701 for(; r; ++r)
00702 {
00703 if(val == *r)
00704 {
00705 return true;
00706 }
00707 }
00708
00709 return false;
00710 }
00711
00712 template< ss_typename_param_k R
00713 , ss_typename_param_k T
00714 >
00715 inline ss_bool_t r_exists_impl(R r, T const& val, iterable_range_tag const&)
00716 {
00717 return std::find(r.begin(), r.end(), val) != r.end();
00718 }
00719
00720 template< ss_typename_param_k R
00721 , ss_typename_param_k T
00722 >
00723 inline ss_bool_t r_exists_impl(R r, T const& val, basic_indirect_range_tag const&)
00724 {
00725 return indirect_range_adaptor<R>(r).exists(val);
00726 }
00727
00728 template< ss_typename_param_k R
00729 , ss_typename_param_k T
00730 >
00731 inline ss_bool_t r_exists_impl(R r, T const& val, indirect_range_tag const&)
00732 {
00733 return r.exists(val);
00734 }
00735
00745 template< ss_typename_param_k R
00746 , ss_typename_param_k T
00747 >
00748 inline ss_bool_t r_exists(R r, T const& val)
00749 {
00750 return r_exists_impl(r, val, r);
00751 }
00752
00753
00754
00755
00756
00757 template< ss_typename_param_k R
00758 , ss_typename_param_k P
00759 >
00760 inline ss_bool_t r_exists_if_1_impl(R r, P pred, notional_range_tag const&)
00761 {
00762 for(; r; ++r)
00763 {
00764 if(pred(*r))
00765 {
00766 return true;
00767 }
00768 }
00769
00770 return false;
00771 }
00772
00773 template< ss_typename_param_k R
00774 , ss_typename_param_k P
00775 >
00776 inline ss_bool_t r_exists_if_1_impl(R r, P pred, iterable_range_tag const&)
00777 {
00778 return std::find_if(r.begin(), r.end(), pred) != r.end();
00779 }
00780
00781 template< ss_typename_param_k R
00782 , ss_typename_param_k P
00783 >
00784 inline ss_bool_t r_exists_if_1_impl(R r, P pred, basic_indirect_range_tag const&)
00785 {
00786 return indirect_range_adaptor<R>(r).exists_if(pred);
00787 }
00788
00789 template< ss_typename_param_k R
00790 , ss_typename_param_k P
00791 >
00792 inline ss_bool_t r_exists_if_1_impl(R r, P pred, indirect_range_tag const&)
00793 {
00794 return r.exists_if(pred);
00795 }
00796
00806 template< ss_typename_param_k R
00807 , ss_typename_param_k P
00808 >
00809 inline ss_bool_t r_exists_if(R r, P pred)
00810 {
00811 return r_exists_if_1_impl(r, pred, r);
00812 }
00813
00814
00815
00816
00817
00818 template< ss_typename_param_k R
00819 , ss_typename_param_k P
00820 , ss_typename_param_k T
00821 >
00822 inline ss_bool_t r_exists_if_2_impl(R r, P pred, T &result, notional_range_tag const&)
00823 {
00824 for(; r; ++r)
00825 {
00826 if(pred(*r))
00827 {
00828 result = *r;
00829
00830 return true;
00831 }
00832 }
00833
00834 return false;
00835 }
00836
00837 template< ss_typename_param_k I
00838 , ss_typename_param_k V
00839 >
00840 inline ss_bool_t r_exists_if_2_impl_helper_(I from, I to, V &val)
00841 {
00842 if(from == to)
00843 {
00844 return false;
00845 }
00846 else
00847 {
00848 val = *from;
00849
00850 return true;
00851 }
00852 }
00853
00854 template< ss_typename_param_k R
00855 , ss_typename_param_k P
00856 , ss_typename_param_k T
00857 >
00858 inline ss_bool_t r_exists_if_2_impl(R r, P pred, T &result, iterable_range_tag const&)
00859 {
00860 return r_exists_if_2_impl_helper_(std::find_if(r.begin(), r.end(), pred), r.end());
00861 }
00862
00863 template< ss_typename_param_k R
00864 , ss_typename_param_k P
00865 , ss_typename_param_k T
00866 >
00867 inline ss_bool_t r_exists_if_2_impl(R r, P pred, T &result, basic_indirect_range_tag const&)
00868 {
00869 return indirect_range_adaptor<R>(r).exists_if(pred, result);
00870 }
00871
00872 template< ss_typename_param_k R
00873 , ss_typename_param_k P
00874 , ss_typename_param_k T
00875 >
00876 inline ss_bool_t r_exists_if_2_impl(R r, P pred, T &result, indirect_range_tag const&)
00877 {
00878 return r.exists_if(pred, result);
00879 }
00880
00891 template< ss_typename_param_k R
00892 , ss_typename_param_k P
00893 , ss_typename_param_k T
00894 >
00895 inline R r_exists_if(R r, P pred, T &result)
00896 {
00897 return r_exists_if_2_impl(r, pred, result, r);
00898 }
00899
00900
00901
00902
00903
00904 template< ss_typename_param_k R
00905 , ss_typename_param_k T
00906 >
00907 inline void r_fill_impl(R r, T const& val, iterable_range_tag const&)
00908 {
00909 std::fill(r.begin(), r.end(), val);
00910 }
00911
00921 template< ss_typename_param_k R
00922 , ss_typename_param_k T
00923 >
00924 inline void r_fill(R r, T const& val)
00925 {
00926 r_fill_impl(r, val, r);
00927 }
00928
00929
00930
00931
00932
00933 template< ss_typename_param_k R
00934 , ss_typename_param_k S
00935 , ss_typename_param_k T
00936 >
00937 inline void r_fill_n_impl(R r, S n, T const& val, iterable_range_tag const&)
00938 {
00939 std::fill(r.begin(), n, val);
00940 }
00941
00952 template< ss_typename_param_k R
00953 , ss_typename_param_k S
00954 , ss_typename_param_k T
00955 >
00956 inline void r_fill_n(R r, S n, T const& val)
00957 {
00958 STLSOFT_ASSERT(n <= r_distance(r));
00959
00960 r_fill_1_impl(r, n, val, r);
00961 }
00962
00963
00964
00965
00966
00967 template< ss_typename_param_k R
00968 , ss_typename_param_k T
00969 >
00970 inline R r_find_impl(R r, T const& val, notional_range_tag const&)
00971 {
00972 for(; r; ++r)
00973 {
00974 if(val == *r)
00975 {
00976 break;
00977 }
00978 }
00979
00980 return r;
00981 }
00982
00983 template< ss_typename_param_k R
00984 , ss_typename_param_k T
00985 >
00986 inline R r_find_impl(R r, T const& val, iterable_range_tag const&)
00987 {
00988 return R(std::find(r.begin(), r.end(), val), r.end());
00989 }
00990
01000 template< ss_typename_param_k R
01001 , ss_typename_param_k T
01002 >
01003 inline R r_find(R r, T const& val)
01004 {
01005 return r_find_impl(r, val, r);
01006 }
01007
01008
01009
01010
01011
01012
01013
01014 template< ss_typename_param_k R
01015 , ss_typename_param_k P
01016 >
01017 inline R r_find_if_impl(R r, P pred, notional_range_tag const&)
01018 {
01019 for(; r; ++r)
01020 {
01021 if(pred(*r))
01022 {
01023 break;
01024 }
01025 }
01026
01027 return r;
01028 }
01029
01030 template< ss_typename_param_k R
01031 , ss_typename_param_k P
01032 >
01033 inline R r_find_if_impl(R r, P pred, iterable_range_tag const&)
01034 {
01035 return R(std::find_if(r.begin(), r.end(), pred), r.end());
01036 }
01037
01047 template< ss_typename_param_k R
01048 , ss_typename_param_k P
01049 >
01050 inline R r_find_if(R r, P pred)
01051 {
01052 return r_find_if_impl(r, pred, r);
01053 }
01054
01055
01056
01057
01058
01059 template< ss_typename_param_k R
01060 , ss_typename_param_k F
01061 >
01062 inline F r_for_each_impl(R r, F f, notional_range_tag const&)
01063 {
01064 for(; r; ++r)
01065 {
01066 f(*r);
01067 }
01068
01069 return f;
01070 }
01071
01072 template< ss_typename_param_k R
01073 , ss_typename_param_k F
01074 >
01075 inline F r_for_each_impl(R r, F f, iterable_range_tag const&)
01076 {
01077 return std::for_each(r.begin(), r.end(), f);
01078 }
01079
01080 template< ss_typename_param_k R
01081 , ss_typename_param_k F
01082 >
01083 inline F r_for_each_impl(R r, F f, basic_indirect_range_tag const&)
01084 {
01085 return indirect_range_adaptor<R>(r).for_each(f);
01086 }
01087
01088 template< ss_typename_param_k R
01089 , ss_typename_param_k F
01090 >
01091 inline F r_for_each_impl(R r, F f, indirect_range_tag const&)
01092 {
01093 return r.for_each(f);
01094 }
01095
01105 template< ss_typename_param_k R
01106 , ss_typename_param_k F
01107 >
01108 inline F r_for_each(R r, F f)
01109 {
01110 return r_for_each_impl(r, f, r);
01111 }
01112
01113
01114
01115
01116
01117 template< ss_typename_param_k R
01118 , ss_typename_param_k F
01119 >
01120 inline void r_generate_impl(R r, F f, iterable_range_tag const&)
01121 {
01122 std::generate(r.begin(), r.end(), f);
01123 }
01124
01134 template< ss_typename_param_k R
01135 , ss_typename_param_k F
01136 >
01137 inline void r_generate(R r, F f)
01138 {
01139 r_generate_impl(r, f, r);
01140 }
01141
01142
01143
01144
01145
01146 template <ss_typename_param_k R>
01147 inline ss_typename_type_ret_k R::value_type r_max_element_1_impl(R r, notional_range_tag const&)
01148 {
01149 typedef ss_typename_type_k R::value_type value_type_t;
01150
01151 value_type_t max_ = value_type_t();
01152
01153 for(; r; ++r)
01154 {
01155 if(max_ < *r)
01156 {
01157 max_ = *r;
01158 }
01159 }
01160
01161 return max_;
01162 }
01163
01164 template <ss_typename_param_k I>
01165 inline I r_max_element_1_impl_iterable(I from, I to)
01166 {
01167 if(from == to)
01168 {
01169 throw empty_range_exception("Cannot determine maximum element of empty range");
01170 }
01171
01172 return std::max_element(from, to);
01173 }
01174
01175 template <ss_typename_param_k R>
01176 inline ss_typename_type_ret_k R::value_type r_max_element_1_impl(R r, iterable_range_tag const&)
01177 {
01178 return *r_max_element_1_impl_iterable(r.begin(), r.end());
01179 }
01180
01181 template <ss_typename_param_k R>
01182 inline ss_typename_type_ret_k R::value_type r_max_element_1_impl(R r, basic_indirect_range_tag const&)
01183 {
01184 return indirect_range_adaptor<R>(r).max_element();
01185 }
01186
01187 template <ss_typename_param_k R>
01188 inline ss_typename_type_ret_k R::value_type r_max_element_1_impl(R r, indirect_range_tag const&)
01189 {
01190 return r.max_element();
01191 }
01192
01202 template <ss_typename_param_k R>
01203 inline ss_typename_type_ret_k R::value_type r_max_element(R r)
01204 {
01205 STLSOFT_ASSERT(r_distance(r) > 0);
01206
01207 return r_max_element_1_impl(r, r);
01208 }
01209
01210
01211
01212
01213
01214 template< ss_typename_param_k I
01215 , ss_typename_param_k F
01216 >
01217 inline I r_max_element_2_impl_iterable(I from, I to, F f)
01218 {
01219 if(from == to)
01220 {
01221 throw empty_range_exception("Cannot determine maximum element of empty range");
01222 }
01223
01224 return std::max_element(from, to, f);
01225 }
01226
01227 template< ss_typename_param_k R
01228 , ss_typename_param_k F
01229 >
01230 inline ss_typename_type_ret_k R::value_type r_max_element_2_impl(R r, F f, iterable_range_tag const&)
01231 {
01232 return *r_max_element_2_impl_iterable(r.begin(), r.end(), f);
01233 }
01234
01235 template< ss_typename_param_k R
01236 , ss_typename_param_k F
01237 >
01238 inline ss_typename_type_ret_k R::value_type r_max_element_2_impl(R r, F f, notional_range_tag const&)
01239 {
01240 typedef ss_typename_type_k R::value_type value_type_t;
01241
01242 value_type_t max_ = value_type_t();
01243
01244 for(; r; ++r)
01245 {
01246 if(f(max_, *r))
01247 {
01248 max_ = *r;
01249 }
01250 }
01251
01252 return max_;
01253 }
01254
01255 template< ss_typename_param_k R
01256 , ss_typename_param_k F
01257 >
01258 inline ss_typename_type_ret_k R::value_type r_max_element_2_impl(R r, F f, basic_indirect_range_tag const&)
01259 {
01260 return indirect_range_adaptor<R>(r).max_element(f);
01261 }
01262
01263 template< ss_typename_param_k R
01264 , ss_typename_param_k F
01265 >
01266 inline ss_typename_type_ret_k R::value_type r_max_element_2_impl(R r, F f, indirect_range_tag const&)
01267 {
01268 return r.max_element(f);
01269 }
01270
01281 template< ss_typename_param_k R
01282 , ss_typename_param_k F
01283 >
01284 inline ss_typename_type_ret_k R::value_type r_max_element(R r, F f)
01285 {
01286 STLSOFT_ASSERT(r_distance(r) > 0);
01287
01288 return r_max_element_2_impl(r, f, r);
01289 }
01290
01291
01292
01293
01294
01295 template <ss_typename_param_k R>
01296 inline ss_typename_type_ret_k R::value_type r_min_element_1_impl(R r, notional_range_tag const&)
01297 {
01298 typedef ss_typename_type_k R::value_type value_type_t;
01299
01300 if(!r)
01301 {
01302 return value_type_t();
01303 }
01304 else
01305 {
01306 value_type_t min_ = *r;
01307
01308 for(; ++r; )
01309 {
01310 if(*r < min_)
01311 {
01312 min_ = *r;
01313 }
01314 }
01315
01316 return min_;
01317 }
01318 }
01319
01320 template <ss_typename_param_k I>
01321 inline I r_min_element_1_impl_iterable(I from, I to)
01322 {
01323 if(from == to)
01324 {
01325 throw empty_range_exception("Cannot determine minimum element of empty range");
01326 }
01327
01328 return std::min_element(from, to);
01329 }
01330
01331 template <ss_typename_param_k R>
01332 inline ss_typename_type_ret_k R::value_type r_min_element_1_impl(R r, iterable_range_tag const&)
01333 {
01334 return *r_min_element_1_impl_iterable(r.begin(), r.end());
01335 }
01336
01337 template <ss_typename_param_k R>
01338 inline ss_typename_type_ret_k R::value_type r_min_element_1_impl(R r, basic_indirect_range_tag const&)
01339 {
01340 return indirect_range_adaptor<R>(r).min_element();
01341 }
01342
01343 template <ss_typename_param_k R>
01344 inline ss_typename_type_ret_k R::value_type r_min_element_1_impl(R r, indirect_range_tag const&)
01345 {
01346 return r.min_element();
01347 }
01348
01358 template <ss_typename_param_k R>
01359 inline ss_typename_type_ret_k R::value_type r_min_element(R r)
01360 {
01361 STLSOFT_ASSERT(r_distance(r) > 0);
01362
01363 return r_min_element_1_impl(r, r);
01364 }
01365
01366
01367
01368
01369
01370 template< ss_typename_param_k I
01371 , ss_typename_param_k F
01372 >
01373 inline I r_min_element_2_impl_iterable(I from, I to, F f)
01374 {
01375 if(from == to)
01376 {
01377 throw empty_range_exception("Cannot determine minimum element of empty range");
01378 }
01379
01380 return std::min_element(from, to, f);
01381 }
01382
01383 template< ss_typename_param_k R
01384 , ss_typename_param_k F
01385 >
01386 inline ss_typename_type_ret_k R::value_type r_min_element_2_impl(R r, F f, iterable_range_tag const&)
01387 {
01388 return *r_min_element_2_impl_iterable(r.begin(), r.end(), f);
01389 }
01390
01391 template< ss_typename_param_k R
01392 , ss_typename_param_k F
01393 >
01394 inline ss_typename_type_ret_k R::value_type r_min_element_2_impl(R r, F f, notional_range_tag const&)
01395 {
01396 typedef ss_typename_type_k R::value_type value_type_t;
01397
01398 value_type_t min_ = value_type_t();
01399
01400 for(; r; ++r)
01401 {
01402 if(f(min_, *r))
01403 {
01404 min_ = *r;
01405 }
01406 }
01407
01408 return min_;
01409 }
01410
01411 template< ss_typename_param_k R
01412 , ss_typename_param_k F
01413 >
01414 inline ss_typename_type_ret_k R::value_type r_min_element_2_impl(R r, F f, basic_indirect_range_tag const&)
01415 {
01416 return indirect_range_adaptor<R>(r).min_element(f);
01417 }
01418
01419 template< ss_typename_param_k R
01420 , ss_typename_param_k F
01421 >
01422 inline ss_typename_type_ret_k R::value_type r_min_element_2_impl(R r, F f, indirect_range_tag const&)
01423 {
01424 return r.min_element(f);
01425 }
01426
01437 template< ss_typename_param_k R
01438 , ss_typename_param_k F
01439 >
01440 inline ss_typename_type_ret_k R::value_type r_min_element(R r, F f)
01441 {
01442 STLSOFT_ASSERT(r_distance(r) > 0);
01443
01444 return r_min_element_2_impl(r, f, r);
01445 }
01446
01447
01448
01449
01450
01451 template< ss_typename_param_k R
01452 , ss_typename_param_k T
01453 >
01454 inline void r_replace_impl(R r, T oldVal, T newVal, iterable_range_tag const&)
01455 {
01456 std::replace(r.begin(), r.end(), oldVal, newVal);
01457 }
01458
01459 template< ss_typename_param_k R
01460 , ss_typename_param_k T
01461 >
01462 inline void r_replace_impl(R r, T oldVal, T newVal, indirect_range_tag const&)
01463 {
01464 r.replace(r, oldVal, newVal);
01465 }
01466
01467
01478 template< ss_typename_param_k R
01479 , ss_typename_param_k T
01480 >
01481 inline void r_replace(R r, T oldVal, T newVal)
01482 {
01483 r_replace_impl(r, oldVal, newVal, r);
01484 }
01485
01486
01487
01488
01489
01490
01491 #if 0
01492 template< ss_typename_param_k RI
01493 , ss_typename_param_k RO
01494 , ss_typename_param_k T
01495 >
01496 inline void r_replace_copy_impl(RI ri, RO ro, T oldVal, T newVal, iterable_range_tag const&, iterable_range_tag const&)
01497 {
01498 std::replace_copy(ri.begin(), ri.end(), ro.begin(), oldVal, newVal);
01499 }
01500
01501 template< ss_typename_param_k RI
01502 , ss_typename_param_k RO
01503 , ss_typename_param_k T
01504 >
01505 inline void r_replace_copy_impl(RI ri, RO ro, T oldVal, T newVal, indirect_range_tag const&, indirect_range_tag const&)
01506 {
01507 ri.replace_copy(ro, oldVal, newVal);
01508 }
01509
01520 template< ss_typename_param_k RI
01521 , ss_typename_param_k RO
01522 , ss_typename_param_k T
01523 >
01524 inline void r_replace_copy(RI ri, RO ro, T oldVal, T newVal)
01525 {
01526 r_replace_copy_impl(ri, ro, oldVal, newVal, ri, ro);
01527 }
01528 #endif
01529
01530
01531
01532
01533
01534 template< ss_typename_param_k R
01535 , ss_typename_param_k P
01536 , ss_typename_param_k T
01537 >
01538 inline void r_replace_if_impl(R r, P pred, T newVal, iterable_range_tag const&)
01539 {
01540 std::replace_if(r.begin(), r.end(), pred, newVal);
01541 }
01542
01543 template< ss_typename_param_k R
01544 , ss_typename_param_k P
01545 , ss_typename_param_k T
01546 >
01547 inline void r_replace_if_impl(R r, P pred, T newVal, indirect_range_tag const&)
01548 {
01549 r.replace_if(r, pred, newVal);
01550 }
01551
01562 template< ss_typename_param_k R
01563 , ss_typename_param_k P
01564 , ss_typename_param_k T
01565 >
01566 inline void r_replace_if(R r, P pred, T newVal)
01567 {
01568 r_replace_if_impl(r, pred, newVal, r);
01569 }
01570
01571
01572
01573
01574
01575
01576 #if 0
01577 template< ss_typename_param_k RI
01578 , ss_typename_param_k RO
01579 , ss_typename_param_k P
01580 , ss_typename_param_k T
01581 >
01582 inline void r_replace_copy_if_impl(RI ri, RO ro, P pred, T newVal, iterable_range_tag const&, iterable_range_tag const&)
01583 {
01584 std::replace_copy_if(ri.begin(), ri.end(), ro.begin(), pred, newVal);
01585 }
01586
01587 template< ss_typename_param_k RI
01588 , ss_typename_param_k RO
01589 , ss_typename_param_k P
01590 , ss_typename_param_k T
01591 >
01592 inline void r_replace_copy_if_impl(RI ri, RO ro, P pred, T newVal, notional_range_tag const&, notional_range_tag const&)
01593 {
01594 for(; ri; ++ri, ++ro)
01595 {
01596 STLSOFT_ASSERT(!(!ro));
01597
01598 if(pred(*ri))
01599 {
01600 *ro = newVal;
01601 }
01602 }
01603 }
01604
01605 template< ss_typename_param_k RI
01606 , ss_typename_param_k RO
01607 , ss_typename_param_k P
01608 , ss_typename_param_k T
01609 >
01610 inline void r_replace_copy_if_impl(RI ri, RO ro, P pred, T newVal, indirect_range_tag const&, indirect_range_tag const&)
01611 {
01612 ri.replace_copy_if(ro, pred, newVal);
01613 }
01614
01615 template< ss_typename_param_k RI
01616 , ss_typename_param_k RO
01617 , ss_typename_param_k P
01618 , ss_typename_param_k T
01619 >
01620 inline void r_replace_copy_if(RI ri, RO ro, P pred, T newVal)
01621 {
01622 r_replace_copy_if_impl(ri, ro, pe, newVal, ri, ro);
01623 }
01624 #endif
01625
01627
01628
01629 #ifdef STLSOFT_UNITTEST
01630 # include "./unittest/algorithms_unittest_.h"
01631 #endif
01632
01633
01634
01635 #ifndef RANGELIB_NO_NAMESPACE
01636 # if defined(_STLSOFT_NO_NAMESPACE) || \
01637 defined(STLSOFT_DOCUMENTATION_SKIP_SECTION)
01638 }
01639 # else
01640 }
01641 }
01642 # endif
01643 #endif
01644
01645
01646
01647 #endif
01648
01649