diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-27 18:24:20 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-27 18:24:20 +0000 |
commit | 483eb2f56657e8e7f419ab1a4fab8dce9ade8609 (patch) | |
tree | e5d88d25d870d5dedacb6bbdbe2a966086a0a5cf /src/boost/libs/sort/example | |
parent | Initial commit. (diff) | |
download | ceph-upstream.tar.xz ceph-upstream.zip |
Adding upstream version 14.2.21.upstream/14.2.21upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'src/boost/libs/sort/example')
25 files changed, 2622 insertions, 0 deletions
diff --git a/src/boost/libs/sort/example/alrbreaker.cpp b/src/boost/libs/sort/example/alrbreaker.cpp new file mode 100644 index 00000000..b93fe89a --- /dev/null +++ b/src/boost/libs/sort/example/alrbreaker.cpp @@ -0,0 +1,78 @@ +// a sorting example that uses the worst-case for conventional MSD radix sorts. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; +using namespace std; + +#define DATA_TYPE boost::uint64_t + +#define ALR_THRESHOLD 3 + +const unsigned max_count = ALR_THRESHOLD - 1; +const unsigned bit_shift = detail::rough_log_2_size(max_count) - + detail::int_log_mean_bin_size; +const unsigned radix_threshold = detail::rough_log_2_size(max_count) + 1; +//Increase this size if too fast to test accurately +const unsigned top_splits = 12; + +const DATA_TYPE typed_one = 1; + +void +fill_vector(vector<DATA_TYPE> & input, const DATA_TYPE base_value, + unsigned remaining_bits) +{ + if (remaining_bits >= radix_threshold) { + input.push_back((base_value << remaining_bits) + + ((typed_one << remaining_bits) - 1)); + fill_vector(input, base_value << bit_shift, remaining_bits - bit_shift); + } + else { + for (unsigned u = 0; u < max_count; ++u) + input.push_back((base_value << remaining_bits) + + (rand() % (1 << remaining_bits))); + } +} + +//Tests spreadsort on the worst-case distribution for standard MSD radix sorts. +int main(int, const char **) { + vector<DATA_TYPE> input; + for (int ii = (1 << top_splits) - 1; ii >= 0; --ii) + fill_vector(input, ii, (sizeof(DATA_TYPE) * 8) - top_splits); + + //Run both std::sort and spreadsort + for (unsigned u = 0; u < 2; ++u) { + vector<DATA_TYPE> array = input; + clock_t start, end; + double elapsed; + start = clock(); + if (u) + std::sort(array.begin(), array.end()); + else + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (u) + printf("std::sort elapsed time %f\n", elapsed / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", elapsed / CLOCKS_PER_SEC); + array.clear(); + } + return 0; +} diff --git a/src/boost/libs/sort/example/alreadysorted.cpp b/src/boost/libs/sort/example/alreadysorted.cpp new file mode 100644 index 00000000..8f56d082 --- /dev/null +++ b/src/boost/libs/sort/example/alreadysorted.cpp @@ -0,0 +1,91 @@ +// spreadsort fully sorted data example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + //Sorts the data once, then times sorting of already-sorted data + loopCount += 1; + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) // EOF or failure stops the reading + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else { + printf("call\n"); + //integer_sort(&(array[0]), &(array[0]) + uCount); + integer_sort(array.begin(), array.end()); + } + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + if (u) + total += elapsed; + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/binaryalrbreaker.cpp b/src/boost/libs/sort/example/binaryalrbreaker.cpp new file mode 100644 index 00000000..c5a163f7 --- /dev/null +++ b/src/boost/libs/sort/example/binaryalrbreaker.cpp @@ -0,0 +1,108 @@ +// a sorting example that uses the worst-case distribution for spreadsort. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; +using namespace std; + +#define DATA_TYPE boost::uint64_t + +#define ALR_THRESHOLD 3 + +const unsigned max_count = ALR_THRESHOLD - 1; +const unsigned bit_shift = detail::rough_log_2_size(max_count) - + detail::int_log_mean_bin_size; +const unsigned radix_threshold = detail::rough_log_2_size(max_count) + 1; + +const DATA_TYPE typed_one = 1; + +void +fill_vector(vector<DATA_TYPE> & input, const DATA_TYPE base_value, + unsigned remaining_bits, const vector<unsigned> & indices, + int index) +{ + if (index < 0) { + for (unsigned u = 0; u < max_count; ++u) + input.push_back((base_value << remaining_bits) + + (rand() % (1 << remaining_bits))); + } + else { + unsigned shift = indices[index]; + fill_vector(input, (base_value << shift) + ((1 << shift) - 1), + remaining_bits - shift, indices, index - 1); + fill_vector(input, base_value << shift, remaining_bits - shift, indices, + index - 1); + } +} + +//Generates a random index from 0 up to but not including count. +unsigned +get_index(unsigned count) +{ + unsigned result = unsigned((rand() % (1 << 16))*uint64_t(count)/(1 << 16)); + if (result >= count) + return count - 1; + return result; +} + +//Tests std::sort vs boost::sort::spreadsort on boost::sort's worst distribution. +int main(int, const char **) { + unsigned total_length = sizeof(DATA_TYPE) * 8; + double std_sort_time = 0; + double spreadsort_time = 0; + for (int repetition = 0; repetition < 10; ++repetition) { + vector<DATA_TYPE> input; + vector<unsigned> offsets; + unsigned bit_length = total_length - radix_threshold; + unsigned bit_offset = bit_shift; + for (; bit_length >= ++bit_offset; bit_length -= bit_offset) + offsets.push_back(bit_offset); + for (int ii = (1 << bit_length) - 1; ii >= 0; --ii) + fill_vector(input, ii, total_length - bit_length, + offsets, offsets.size() - 1); + + //Randomize the inputs slightly so they aren't in reverse-sorted order, for + //which std::sort is very fast. + for (unsigned u = 0; u < input.size() / 10; ++u) + std::swap(input[get_index(input.size())], input[get_index(input.size())]); + + //Run both std::sort and boost::sort::spreadsort. + for (unsigned u = 0; u < 2; ++u) { + vector<DATA_TYPE> array = input; + clock_t start, end; + double elapsed; + start = clock(); + if (u) + std::sort(array.begin(), array.end()); + else + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (u) + std_sort_time += elapsed / CLOCKS_PER_SEC; + else + spreadsort_time += elapsed / CLOCKS_PER_SEC; + array.clear(); + } + } + + printf("std::sort elapsed time %f\n", std_sort_time); + printf("spreadsort elapsed time %f\n", spreadsort_time); + return 0; +} diff --git a/src/boost/libs/sort/example/boostrandomgen.cpp b/src/boost/libs/sort/example/boostrandomgen.cpp new file mode 100644 index 00000000..74f9b526 --- /dev/null +++ b/src/boost/libs/sort/example/boostrandomgen.cpp @@ -0,0 +1,69 @@ +// a random number generator supporting different distributions. +// +// Copyright Steven Ross 2009. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <stdio.h> +#include "stdlib.h" +#include <fstream> +#include <iostream> +#include <vector> +#include <string> +#include <boost/random.hpp> + +using std::string; +using namespace boost; + +int main(int argc, const char ** argv) { + //Always seed with the same value, to get the same results + srand(1); + //defaults + int mod_shift = 32; + unsigned count = 1000000; + //Reading in user arguments + if (argc > 2) + count = atoi(argv[2]); + if (argc > 1) + mod_shift = atoi(argv[1]) - 1; + std::ofstream ofile; + ofile.open("input.txt", std::ios_base::out | std::ios_base::binary | + std::ios_base::trunc); + if (ofile.bad()) { + printf("could not open input.txt for writing!\n"); + return 1; + } + int min_int = (std::numeric_limits<int>::min)(); + int max_int = (std::numeric_limits<int>::max)(); + if (mod_shift < 31 && mod_shift >= 0) { + max_int %= 1 << mod_shift; + if (-max_int > min_int) + min_int = -max_int; + } + std::vector<int> result; + result.resize(count); + mt19937 rng; + if (argc > 3 && (string(argv[3]) == "-normal")) { + boost::normal_distribution<> everything(0, max_int/4); + variate_generator<mt19937&,normal_distribution<> > gen(rng, everything); + generate(result.begin(), result.end(), gen); + } + else if (argc > 3 && (string(argv[3]) == "-lognormal")) { + lognormal_distribution<> everything(max_int/2, max_int/4); + variate_generator<mt19937&,lognormal_distribution<> > gen(rng, everything); + generate(result.begin(), result.end(), gen); + } + else { + uniform_int<> everything(min_int, max_int); + variate_generator<mt19937&,uniform_int<> > gen(rng, everything); + generate(result.begin(), result.end(), gen); + } + ofile.write(reinterpret_cast<char *>(&(result[0])), result.size() * + sizeof(int)); + ofile.close(); + return 0; +} diff --git a/src/boost/libs/sort/example/caseinsensitive.cpp b/src/boost/libs/sort/example/caseinsensitive.cpp new file mode 100644 index 00000000..26d1c4f0 --- /dev/null +++ b/src/boost/libs/sort/example/caseinsensitive.cpp @@ -0,0 +1,101 @@ +// Example of sorting a struct using a case-insensitive string key. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/algorithm/string.hpp> +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +struct DATA_TYPE { + string a; +}; + +struct lessthan { + inline bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + return boost::algorithm::ilexicographical_compare(x.a, y.a); + } +}; + +struct bracket { + inline unsigned char operator()(const DATA_TYPE &x, size_t offset) const { + return toupper(x.a[offset]); + } +}; + +struct getsize { + inline size_t operator()(const DATA_TYPE &x) const{ return x.a.size(); } +}; + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + indata >> inval.a; + while (!indata.eof() ) { + array.push_back(inval); + indata >> inval.a; + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + std::sort(array.begin(), array.end(), lessthan()); + else + string_sort(array.begin(), array.end(), bracket(), getsize(), lessthan()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u].a << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/charstringsample.cpp b/src/boost/libs/sort/example/charstringsample.cpp new file mode 100644 index 00000000..4f4487d8 --- /dev/null +++ b/src/boost/libs/sort/example/charstringsample.cpp @@ -0,0 +1,101 @@ +// Example of sorting structs with a string key and indexing functors. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +struct DATA_TYPE { + string a; + inline bool operator<(const DATA_TYPE &y) const { return a < y.a;} +}; + + +struct bracket { + inline unsigned char operator()(const DATA_TYPE &x, size_t offset) const { + return x.a[offset]; + } +}; + +struct getsize { + inline size_t operator()(const DATA_TYPE &x) const{ return x.a.size(); } +}; + + + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + indata >> inval.a; + while (!indata.eof() ) { + array.push_back(inval); + indata >> inval.a; + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) { + std::sort(array.begin(), array.end()); + } else { +//[bracket_1 + string_sort(array.begin(), array.end(), bracket(), getsize()); +//] [/bracket_1] + } + end = clock(); + elapsed = static_cast<double>(end - start); + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + ofile << array[u].a << "\n"; + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/double.cpp b/src/boost/libs/sort/example/double.cpp new file mode 100644 index 00000000..eff1295e --- /dev/null +++ b/src/boost/libs/sort/example/double.cpp @@ -0,0 +1,105 @@ +// spreadsort double sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE double +#define CAST_TYPE boost::int64_t + +//Pass in an argument to test std::sort +//Note that this converts NaNs and -0.0 to 0.0, so that sorting results are +//identical every time +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Using this to support compilers that don't support 64-bit constants + CAST_TYPE exponent_mask = 0x7ff00000; + exponent_mask <<= 32; + CAST_TYPE top_exponent_bit = 0x40000000; + top_exponent_bit <<= 32; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) { + input.read(reinterpret_cast<char *>(&(array[v])), uSize ); + //Checking for denormalized numbers + if (!(float_mem_cast<DATA_TYPE, CAST_TYPE>(array[v]) & exponent_mask)) { + //Make the top exponent bit high + CAST_TYPE temp = top_exponent_bit | + float_mem_cast<DATA_TYPE, CAST_TYPE>(array[v]); + memcpy(&(array[v]), &temp, sizeof(DATA_TYPE)); + } + //Testcase doesn't sort NaNs; they just cause confusion + if (!(array[v] < 0.0) && !(0.0 < array[v])) + array[v] = 0.0; + ++v; + } + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //float_sort(&(array[0]), &(array[0]) + uCount); + float_sort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/floatfunctorsample.cpp b/src/boost/libs/sort/example/floatfunctorsample.cpp new file mode 100644 index 00000000..e930fee4 --- /dev/null +++ b/src/boost/libs/sort/example/floatfunctorsample.cpp @@ -0,0 +1,138 @@ +// spreadsort float functor sorting example. +// +// Copyright Steven Ross 2009. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +// Caution: this file contains Quickbook markup as well as code +// and comments, don't change any of the special comment markups! + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> + +using namespace boost::sort::spreadsort; + +//[float_functor_types +#define CAST_TYPE int +#define KEY_TYPE float +//] [/float_functor_types] + + +//[float_functor_datatypes +struct DATA_TYPE { + KEY_TYPE key; + std::string data; +}; +//] [/float_functor_datatypes] + + +//[float_functor_rightshift +// Casting to an integer before bitshifting +struct rightshift { + int operator()(const DATA_TYPE &x, const unsigned offset) const { + return float_mem_cast<KEY_TYPE, CAST_TYPE>(x.key) >> offset; + } +}; +//] [/float_functor_rightshift] + +//[float_functor_lessthan +struct lessthan { + bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + return x.key < y.key; + } +}; +//] [/float_functor_lessthan] + +// Pass in an argument to test std::sort +// Note that this converts NaNs and -0.0 to 0.0, so that sorting results are +// identical every time +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) { + input.read(reinterpret_cast<char *>(&(array[v].key)), + sizeof(array[v].key)); + //Checking for denormalized numbers; float_sort looks too fast on them. + if (!(float_mem_cast<KEY_TYPE, CAST_TYPE>(array[v].key) & 0x7f800000)) { + //Make the top exponent bit high + CAST_TYPE temp = 0x40000000 | + float_mem_cast<KEY_TYPE, CAST_TYPE>(array[v].key); + memcpy(&(array[v].key), &temp, sizeof(KEY_TYPE)); + } + //Testcase doesn't sort NaNs; they just cause confusion + if (!(array[v].key < 0.0) && !(0.0 < array[v].key)) + array[v].key = 0.0; + //Adding the data, in this case a string + std::stringstream intstr; + intstr << array[v].key; + array[v].data = intstr.str(); + ++v; + } + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + std::sort(array.begin(), array.end(), lessthan()); + else + float_sort(array.begin(), array.end(), rightshift(), lessthan()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v].key)), + sizeof(array[v].key)); + ofile << array[v].data; + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/floatsample.cpp b/src/boost/libs/sort/example/floatsample.cpp new file mode 100644 index 00000000..1de3f650 --- /dev/null +++ b/src/boost/libs/sort/example/floatsample.cpp @@ -0,0 +1,100 @@ +// spreadsort float sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE float +#define CAST_TYPE int + +//Pass in an argument to test std::sort +//Note that this converts NaNs and -0.0 to 0.0, so that sorting results are +//identical every time +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) { + input.read(reinterpret_cast<char *>(&(array[v])), uSize ); + //Checking for denormalized numbers + if (!(float_mem_cast<float, int>(array[v]) & 0x7f800000)) { + //Make the top exponent bit high + CAST_TYPE temp = 0x40000000 | float_mem_cast<float, int>(array[v]); + memcpy(&(array[v]), &temp, sizeof(DATA_TYPE)); + } + //Testcase doesn't sort NaNs; they just cause confusion + if (!(array[v] < 0.0) && !(0.0 < array[v])) + array[v] = 0.0; + ++v; + } + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //boost::sort::spreadsort::spreadsort(&(array[0]), &(array[0]) + uCount); + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + input.close(); + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/generalizedstruct.cpp b/src/boost/libs/sort/example/generalizedstruct.cpp new file mode 100644 index 00000000..eed82c9e --- /dev/null +++ b/src/boost/libs/sort/example/generalizedstruct.cpp @@ -0,0 +1,192 @@ +// This example shows how to sort structs using complex multiple part keys using +// string_sort. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <boost/sort/spreadsort/float_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +//[generalized_functors +struct DATA_TYPE { + time_t birth; + float net_worth; + string first_name; + string last_name; +}; + +static const int birth_size = sizeof(time_t); +static const int first_name_offset = birth_size + sizeof(float); +static const boost::uint64_t base_mask = 0xff; + +struct lessthan { + inline bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + if (x.birth != y.birth) { + return x.birth < y.birth; + } + if (x.net_worth != y.net_worth) { + return x.net_worth < y.net_worth; + } + if (x.first_name != y.first_name) { + return x.first_name < y.first_name; + } + return x.last_name < y.last_name; + } +}; + +struct bracket { + inline unsigned char operator()(const DATA_TYPE &x, size_t offset) const { + // Sort date as a signed int, returning the appropriate byte. + if (offset < birth_size) { + const int bit_shift = 8 * (birth_size - offset - 1); + unsigned char result = (x.birth & (base_mask << bit_shift)) >> bit_shift; + // Handling the sign bit. Unnecessary if the data is always positive. + if (offset == 0) { + return result ^ 128; + } + + return result; + } + + // Sort a signed float. This requires reversing the order of negatives + // because of the way floats are represented in bits. + if (offset < first_name_offset) { + const int bit_shift = 8 * (first_name_offset - offset - 1); + unsigned key = float_mem_cast<float, unsigned>(x.net_worth); + unsigned char result = (key & (base_mask << bit_shift)) >> bit_shift; + // Handling the sign. + if (x.net_worth < 0) { + return 255 - result; + } + // Increasing positives so they are higher than negatives. + if (offset == birth_size) { + return 128 + result; + } + + return result; + } + + // Sort a string that is before the end. This approach supports embedded + // nulls. If embedded nulls are not required, then just delete the "* 2" + // and the inside of the following if just becomes: + // return x.first_name[offset - first_name_offset]; + const unsigned first_name_end_offset = + first_name_offset + x.first_name.size() * 2; + if (offset < first_name_end_offset) { + int char_offset = offset - first_name_offset; + // This signals that the string continues. + if (!(char_offset & 1)) { + return 1; + } + return x.first_name[char_offset >> 1]; + } + + // This signals that the string has ended, so that shorter strings come + // before longer ones. + if (offset == first_name_end_offset) { + return 0; + } + + // The final string needs no special consideration. + return x.last_name[offset - first_name_end_offset - 1]; + } +}; + +struct getsize { + inline size_t operator()(const DATA_TYPE &x) const { + return first_name_offset + x.first_name.size() * 2 + 1 + + x.last_name.size(); + } +}; +//] [/generalized_functors] + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + + // Read in the data. + DATA_TYPE inval; + while (!indata.eof() ) { + indata >> inval.first_name; + indata >> inval.last_name; + indata.read(reinterpret_cast<char *>(&(inval.birth)), birth_size); + indata.read(reinterpret_cast<char *>(&(inval.net_worth)), sizeof(float)); + // Handling nan. + if (inval.net_worth != inval.net_worth) { + inval.net_worth = 0; + } + if (indata.eof()) + break; + array.push_back(inval); + } + indata.close(); + + // Sort the data. + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) { + std::sort(array.begin(), array.end(), lessthan()); + } else { +//[generalized_functors_call + string_sort(array.begin(), array.end(), bracket(), getsize(), lessthan()); +//] [/generalized_functors_call] + } + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) { + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + } else { + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + } + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u].birth << " " << array[u].net_worth << " " + << array[u].first_name << " " << array[u].last_name << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) { + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + } else { + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + } + return 0; +} diff --git a/src/boost/libs/sort/example/int64.cpp b/src/boost/libs/sort/example/int64.cpp new file mode 100644 index 00000000..e01ce5c7 --- /dev/null +++ b/src/boost/libs/sort/example/int64.cpp @@ -0,0 +1,93 @@ +// spreadsort 64-bit integer sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +//[int64bit_1 +#define DATA_TYPE boost::int64_t +//] [/int64bit_1] + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + if (v < uCount) + array.resize(v); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //boost::sort::spreadsort::spreadsort(&(array[0]), &(array[0]) + uCount); +//[int64bit_2 + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); +//] [/int64bit_2] + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + input.close(); + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/keyplusdatasample.cpp b/src/boost/libs/sort/example/keyplusdatasample.cpp new file mode 100644 index 00000000..bb6d30c6 --- /dev/null +++ b/src/boost/libs/sort/example/keyplusdatasample.cpp @@ -0,0 +1,107 @@ +// spreadsort key and data sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +struct DATA_TYPE { + int key; + std::string data; + }; +//functor example +struct lessthan { + inline bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + return x.key < y.key; + } +}; + +struct rightshift { + inline int operator()(const DATA_TYPE &x, const unsigned offset) { + return x.key >> offset; + } +}; + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uSize = sizeof(int); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + double total = 0.0; + std::vector<DATA_TYPE> array; + array.reserve(length/uSize); + unsigned uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + unsigned v = 0; + while (input.good() && v++ < uCount) { // EOF or failure stops the reading + DATA_TYPE element; + input.read(reinterpret_cast<char *>(&(element.key)), sizeof(element.key)); + std::stringstream intstr; + intstr << element.key; + element.data = intstr.str(); + array.push_back(element); + } + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + std::sort(array.begin(), array.end(), lessthan()); + else + integer_sort(array.begin(), array.end(), rightshift(), lessthan()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v].key)), + sizeof(array[v].key)); + ofile << array[v].data; + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + input.close(); + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/mostlysorted.cpp b/src/boost/libs/sort/example/mostlysorted.cpp new file mode 100644 index 00000000..b609cbdb --- /dev/null +++ b/src/boost/libs/sort/example/mostlysorted.cpp @@ -0,0 +1,100 @@ +// spreadsort on a mostly sorted array example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + +unsigned +get_index(unsigned count) +{ + unsigned result = unsigned((rand() % (1 << 16))*uint64_t(count)/(1 << 16)); + if (result >= count || result < 0) + result = count - 1; + return result; +} + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + srand(1); + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + //Sorts the data once, then times sorting of already-sorted data + loopCount += 1; + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) // EOF or failure stops the reading + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + for (unsigned v = 0; v < uCount/10; ++v) + std::swap(array[get_index(uCount)], array[get_index(uCount)]); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //integer_sort(&(array[0]), &(array[0]) + uCount); + integer_sort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + if (u) + total += elapsed; + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/parallelint.cpp b/src/boost/libs/sort/example/parallelint.cpp new file mode 100644 index 00000000..e7806617 --- /dev/null +++ b/src/boost/libs/sort/example/parallelint.cpp @@ -0,0 +1,115 @@ +// Benchmark for integer sorting speed across parallel threads. +// +// Copyright Steven Ross 2014 +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <boost/thread.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + +bool is_sorted(const std::vector<DATA_TYPE> &array) { + for (unsigned u = 0; u + 1 < array.size(); ++u) { + if (array[u] > array[u + 1]) { + return false; + } + } + return true; +} + +void sort_loop(const std::vector<DATA_TYPE> &base_array, bool stdSort, + unsigned loopCount) { + std::vector<DATA_TYPE> array(base_array); + for (unsigned u = 0; u < loopCount; ++u) { + for (unsigned v = 0; v < base_array.size(); ++v) { + array[v] = base_array[v]; + } + if (stdSort) + std::sort(array.begin(), array.end()); + else + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + if (!is_sorted(array)) { + fprintf(stderr, "sort failed!\n"); + exit(1); + } + } +} + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + int threadCount = -1; + unsigned loopCount = 0; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else if(threadCount < 0) + threadCount = atoi(argv[u]); + else + loopCount = atoi(argv[u]); + } + if (!loopCount) { + loopCount = 1; + } + printf("threads: %d loops: %d\n", threadCount, loopCount); + + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + std::vector<DATA_TYPE> base_array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + base_array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) + input.read(reinterpret_cast<char *>(&(base_array[v++])), uSize ); + input.close(); + if (v < uCount) + base_array.resize(v); + //Run multiple loops, if requested + clock_t start, end; + double elapsed; + std::vector<boost::thread *> workers; + start = clock(); + if (threadCount == 0) { + sort_loop(base_array, stdSort, loopCount); + } else { + for (int i = 0; i < threadCount; ++i) { + workers.push_back(new boost::thread(sort_loop, base_array, stdSort, + loopCount)); + } + for (int i = 0; i < threadCount; ++i) { + workers[i]->join(); + delete workers[i]; + } + } + end = clock(); + elapsed = static_cast<double>(end - start) ; + + if (stdSort) + printf("std::sort clock time %lf\n", elapsed/CLOCKS_PER_SEC/threadCount); + else + printf("spreadsort clock time %lf\n", elapsed/CLOCKS_PER_SEC/threadCount); + return 0; +} diff --git a/src/boost/libs/sort/example/parallelstring.cpp b/src/boost/libs/sort/example/parallelstring.cpp new file mode 100644 index 00000000..fb86604a --- /dev/null +++ b/src/boost/libs/sort/example/parallelstring.cpp @@ -0,0 +1,143 @@ +// Benchmark for integer sorting speed across parallel threads. +// +// Copyright Steven Ross 2014 +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/random/mersenne_twister.hpp> +#include <boost/random/uniform_int_distribution.hpp> +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <boost/thread.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +#define DATA_TYPE string + +static bool is_sorted(const std::vector<DATA_TYPE> &array) { + for (unsigned u = 0; u + 1 < array.size(); ++u) { + if (array[u] > array[u + 1]) { + return false; + } + } + return true; +} + +static void sort_core(std::vector<DATA_TYPE> &array, bool stdSort, + unsigned loopCount) { + if (stdSort) + std::sort(array.begin(), array.end()); + else + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + if (!is_sorted(array)) { + fprintf(stderr, "sort failed!\n"); + exit(1); + } +} + +static void sort_loop(const std::vector<DATA_TYPE> &base_array, bool stdSort, + unsigned loopCount) { + std::vector<DATA_TYPE> array(base_array); + for (unsigned u = 0; u < loopCount; ++u) { + for (unsigned v = 0; v < base_array.size(); ++v) { + array[v] = base_array[v]; + } + sort_core(array, stdSort, loopCount); + } +} + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + int constant_to_random_ratio = -1; + int threadCount = -1; + unsigned loopCount = 0; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else if(threadCount < 0) + threadCount = atoi(argv[u]); + else if (!loopCount) + loopCount = atoi(argv[u]); + else + constant_to_random_ratio = atoi(argv[u]); + } + if (!loopCount) { + loopCount = 1; + } + printf("threads: %d loops: %d\n", threadCount, loopCount); + + std::vector<DATA_TYPE> base_array; + if (constant_to_random_ratio >= 0) { + //Test for random data with gaps of identical data. + random::mt19937 generator; + random::uniform_int_distribution<int> distribution(0,255); + const int constant_to_random_count = 1000000; + const int string_length = 1000; + for (int i = 0; i < constant_to_random_count; ++i) { + DATA_TYPE temp(string_length, 'x'); // fill with default character. + for (int j = constant_to_random_ratio; j < string_length;) { + int val = distribution(generator); + temp[j] = val; + j += (val * constant_to_random_ratio)/128 + 1; + } + base_array.push_back(temp); + } + } else { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + while (!indata.eof() ) { + indata >> inval; + base_array.push_back(inval); + } + } + + // Sort the input + clock_t start, end; + double elapsed; + std::vector<boost::thread *> workers; + start = clock(); + if (threadCount == 0) { + if (loopCount > 1) { + sort_loop(base_array, stdSort, loopCount); + } else { + sort_core(base_array, stdSort, loopCount); + } + threadCount = 1; + } else { + for (int i = 0; i < threadCount; ++i) { + workers.push_back(new boost::thread(sort_loop, base_array, stdSort, + loopCount)); + } + for (int i = 0; i < threadCount; ++i) { + workers[i]->join(); + delete workers[i]; + } + } + end = clock(); + elapsed = static_cast<double>(end - start) ; + + printf("for %lu strings\n", base_array.size()); + if (stdSort) + printf("std::sort clock time %lf\n", elapsed/CLOCKS_PER_SEC/threadCount); + else + printf("spreadsort clock time %lf\n", elapsed/CLOCKS_PER_SEC/threadCount); + return 0; +} diff --git a/src/boost/libs/sort/example/randomgen.cpp b/src/boost/libs/sort/example/randomgen.cpp new file mode 100644 index 00000000..aaa1f850 --- /dev/null +++ b/src/boost/libs/sort/example/randomgen.cpp @@ -0,0 +1,69 @@ +// flexible random number generator providing multiple distributions. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/random/mersenne_twister.hpp> +#include <boost/random/uniform_int_distribution.hpp> +#include <stdio.h> +#include "stdlib.h" +#include <fstream> +#include <iostream> +using namespace boost; + +int main(int argc, const char ** argv) { + random::mt19937 generator; + random::uniform_int_distribution<unsigned> distribution; + //defaults + unsigned high_shift = 16; + unsigned low_shift = 16; + unsigned count = 1000000; + //Reading in user arguments + if (argc > 1) + high_shift = atoi(argv[1]); + if (argc > 2) + low_shift = atoi(argv[2]); + if (argc > 3) + count = atoi(argv[3]); + if (high_shift > 16) + high_shift = 16; + if (low_shift > 16) + low_shift = 16; + std::ofstream ofile; + ofile.open("input.txt", std::ios_base::out | std::ios_base::binary | + std::ios_base::trunc); + if (ofile.bad()) { + printf("could not open input.txt for writing!\n"); + return 1; + } + //buffering file output for speed + unsigned uDivideFactor = 1000; + //Skipping buffering for small files + if (count < uDivideFactor * 100) + uDivideFactor = count; + unsigned * pNumbers = static_cast<unsigned *>(malloc(uDivideFactor * + sizeof(unsigned))); + //Generating semirandom numbers + unsigned mask = 0; + unsigned one = 1; + for (unsigned u = 0; u < low_shift; ++u) { + mask += one << u; + } + for (unsigned u = 0; u < high_shift; ++u) { + mask += one << (16 + u); + } + for (unsigned u = 0; u < count/uDivideFactor; ++u) { + unsigned i = 0; + for (; i< uDivideFactor; ++i) { + pNumbers[i] = distribution(generator) & mask; + } + ofile.write(reinterpret_cast<char *>(pNumbers), uDivideFactor * 4 ); + } + ofile.close(); + return 0; +} diff --git a/src/boost/libs/sort/example/reverseintsample.cpp b/src/boost/libs/sort/example/reverseintsample.cpp new file mode 100644 index 00000000..c4777be9 --- /dev/null +++ b/src/boost/libs/sort/example/reverseintsample.cpp @@ -0,0 +1,101 @@ +//! \file +//! \brief integer sort with a rightshift functor reverse sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +// Caution: this file contains Quickbook markup as well as code +// and comments, don't change any of the special comment markups! + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <iostream> +#include <functional> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + +struct negrightshift { + inline int operator()(const int &x, const unsigned offset) { + return -(x >> offset); + } +}; + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + if (v < uCount) + array.resize(v); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + +//[reverse_int_1 + std::sort(array.begin(), array.end(), std::greater<DATA_TYPE>()); +//] [/reverse_int_1] + else +//[reverse_int_2 + integer_sort(array.begin(), array.end(), negrightshift(), std::greater<DATA_TYPE>()); +//] [/reverse_int_2] + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v])); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/reversestringfunctorsample.cpp b/src/boost/libs/sort/example/reversestringfunctorsample.cpp new file mode 100644 index 00000000..6066f281 --- /dev/null +++ b/src/boost/libs/sort/example/reversestringfunctorsample.cpp @@ -0,0 +1,112 @@ +// spreadsort string functor reverse sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +struct DATA_TYPE { + string a; + }; + +struct greaterthan { + inline bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + return x.a > y.a; + } +}; + +struct bracket { + inline unsigned char operator()(const DATA_TYPE &x, size_t offset) const { + return x.a[offset]; + } +}; + +struct getsize { + inline size_t operator()(const DATA_TYPE &x) const{ return x.a.size(); } +}; + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (!indata) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + indata >> inval.a; + while (!indata.eof() ) { + array.push_back(inval); + //Inserting embedded nulls and empty strings + if (!(array.size() % 100)) { + if (inval.a.empty() || !(array.size() % 1000)) { + inval.a = ""; + array.push_back(inval); + } + else { + inval.a[0] = '\0'; + array.push_back(inval); + } + } + indata >> inval.a; + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + std::sort(array.begin(), array.end(), greaterthan()); + else + reverse_string_sort(array.begin(), array.end(), bracket(), getsize(), + greaterthan()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u].a << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/reversestringsample.cpp b/src/boost/libs/sort/example/reversestringsample.cpp new file mode 100644 index 00000000..9fa04c46 --- /dev/null +++ b/src/boost/libs/sort/example/reversestringsample.cpp @@ -0,0 +1,98 @@ +// spreadsort reverse string sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +#define DATA_TYPE string + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (!indata) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + indata >> inval; + while (!indata.eof() ) { + //testing substrings + if (!(array.size() % 2)) + inval = "prefix" + inval; + else + inval += "suffix"; + array.push_back(inval); + //Inserting embedded nulls and empty strings + if (!(array.size() % 100)) { + if (inval.empty() || !(array.size() % 1000)) + array.push_back(""); + else { + inval[0] = '\0'; + array.push_back(inval); + } + } + indata >> inval; + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end(), std::greater<string>()); + else + //string_sort(&(array[0]), &(array[0]) + uCount); + reverse_string_sort(array.begin(), array.end(), std::greater<string>()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u] << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/rightshiftsample.cpp b/src/boost/libs/sort/example/rightshiftsample.cpp new file mode 100644 index 00000000..33da64f7 --- /dev/null +++ b/src/boost/libs/sort/example/rightshiftsample.cpp @@ -0,0 +1,98 @@ +//! \brief Integer sort with a rightshift functor sorting example. +//! \file +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +// Caution: this file contains Quickbook markup as well as code +// and comments, don't change any of the special comment markups! + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + +//[rightshift_int_functor +struct rightshift { + inline int operator()(DATA_TYPE x, unsigned offset) { return x >> offset; } +}; +//] [/rightshift_int_functor] + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + if (v < uCount) + array.resize(v); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) { + std::sort(array.begin(), array.end()); + } else { +//[rightshift_1 + integer_sort(array.begin(), array.end(), rightshift()); +//] [/rightshift_1] + } + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/sample.cpp b/src/boost/libs/sort/example/sample.cpp new file mode 100644 index 00000000..1da89368 --- /dev/null +++ b/src/boost/libs/sort/example/sample.cpp @@ -0,0 +1,88 @@ +// spreadsort sorting example +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <sstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE int + + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) + input.read(reinterpret_cast<char *>(&(array[v++])), uSize ); + if (v < uCount) + array.resize(v); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + std::sort(array.begin(), array.end()); + else + boost::sort::spreadsort::spreadsort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start); + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + input.close(); + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/shiftfloatsample.cpp b/src/boost/libs/sort/example/shiftfloatsample.cpp new file mode 100644 index 00000000..5f752745 --- /dev/null +++ b/src/boost/libs/sort/example/shiftfloatsample.cpp @@ -0,0 +1,107 @@ +// float_sort rightshift functor sorting example +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/spreadsort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <string> +#include <fstream> +#include <iostream> +using namespace boost::sort::spreadsort; + +#define DATA_TYPE float +#define CAST_TYPE int + +//Casting to an integer before bitshifting +struct rightshift { + inline int operator()(const DATA_TYPE &x, const unsigned offset) const { + return float_mem_cast<DATA_TYPE, int>(x) >> offset; + } +}; + + +//Pass in an argument to test std::sort +//Note that this converts NaNs and -0.0 to 0.0, so that sorting results are +//identical every time +int main(int argc, const char ** argv) { + size_t uCount,uSize=sizeof(DATA_TYPE); + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + std::ifstream input("input.txt", std::ios_base::in | std::ios_base::binary); + if (input.fail()) { + printf("input.txt could not be opened\n"); + return 1; + } + double total = 0.0; + std::vector<DATA_TYPE> array; + input.seekg (0, std::ios_base::end); + size_t length = input.tellg(); + uCount = length/uSize; + //Run multiple loops, if requested + for (unsigned u = 0; u < loopCount; ++u) { + input.seekg (0, std::ios_base::beg); + //Conversion to a vector + array.resize(uCount); + unsigned v = 0; + while (input.good() && v < uCount) { + input.read(reinterpret_cast<char *>(&(array[v])), uSize ); + //Testcase doesn't sort NaNs; they just cause confusion + if (!(array[v] < 0.0) && !(0.0 < array[v])) + array[v] = 0.0; + //Checking for denormalized numbers + if (!(float_mem_cast<float, int>(array[v]) & 0x7f800000)) { + //Make the top exponent bit high + CAST_TYPE temp = 0x40000000 | float_mem_cast<float, int>(array[v]); + memcpy(&(array[v]), &temp, sizeof(DATA_TYPE)); + } + ++v; + } + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //float_sort(&(array[0]), &(array[0]) + uCount, rightshift()); + float_sort(array.begin(), array.end(), rightshift()); + end = clock(); + elapsed = static_cast<double>(end - start) ; + std::ofstream ofile; + if (stdSort) + ofile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + ofile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (ofile.good()) { + for (unsigned v = 0; v < array.size(); ++v) { + ofile.write(reinterpret_cast<char *>(&(array[v])), sizeof(array[v]) ); + } + ofile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} diff --git a/src/boost/libs/sort/example/stringfunctorsample.cpp b/src/boost/libs/sort/example/stringfunctorsample.cpp new file mode 100644 index 00000000..0ef9bf4e --- /dev/null +++ b/src/boost/libs/sort/example/stringfunctorsample.cpp @@ -0,0 +1,127 @@ +//! \brief spreadsort string functor sorting example. +//! \file +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +// Caution: this file contains Quickbook markup as well as code +// and comments, don't change any of the special comment markups! + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +struct DATA_TYPE { + string a; +}; + +//[lessthan_functor + +struct lessthan { + inline bool operator()(const DATA_TYPE &x, const DATA_TYPE &y) const { + return x.a < y.a; + } +}; +//] [/lessthan_functor] + +//[bracket_functor +struct bracket { + inline unsigned char operator()(const DATA_TYPE &x, size_t offset) const { + return x.a[offset]; + } +}; +//] [/bracket_functor] + +//[getsize_functor +struct getsize { + inline size_t operator()(const DATA_TYPE &x) const{ return x.a.size(); } +}; +//] [/getsize_functor] + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + indata >> inval.a; + while (!indata.eof() ) { + array.push_back(inval); + //Inserting embedded nulls and empty strings + if (!(array.size() % 100)) { + if (inval.a.empty() || !(array.size() % 1000)) { + inval.a = ""; + array.push_back(inval); + } + else { + inval.a[0] = '\0'; + array.push_back(inval); + } + } + indata >> inval.a; + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) { + std::sort(array.begin(), array.end(), lessthan()); + } else { +//[stringsort_functors_call + string_sort(array.begin(), array.end(), bracket(), getsize(), lessthan()); +//] [/stringsort_functors_call] + } + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) { + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + } else { + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + } + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u].a << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) { + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + } else { + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + } + return 0; +} diff --git a/src/boost/libs/sort/example/stringsample.cpp b/src/boost/libs/sort/example/stringsample.cpp new file mode 100644 index 00000000..eb300338 --- /dev/null +++ b/src/boost/libs/sort/example/stringsample.cpp @@ -0,0 +1,85 @@ +// spreadsort string sorting example. +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::string; +using namespace boost::sort::spreadsort; + +#define DATA_TYPE string + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + DATA_TYPE inval; + while (!indata.eof() ) { + indata >> inval; + array.push_back(inval); + } + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //string_sort(&(array[0]), &(array[0]) + uCount); + string_sort(array.begin(), array.end()); + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u) + outfile << array[u] << "\n"; + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} + + diff --git a/src/boost/libs/sort/example/wstringsample.cpp b/src/boost/libs/sort/example/wstringsample.cpp new file mode 100644 index 00000000..6775bbe7 --- /dev/null +++ b/src/boost/libs/sort/example/wstringsample.cpp @@ -0,0 +1,96 @@ +// spreadsort wstring sorting example +// +// Copyright Steven Ross 2009-2014. +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +// See http://www.boost.org/libs/sort for library home page. + +#include <boost/sort/spreadsort/string_sort.hpp> +#include <time.h> +#include <stdio.h> +#include <stdlib.h> +#include <algorithm> +#include <vector> +#include <iostream> +#include <fstream> +#include <string> +using std::wstring; +using namespace boost::sort::spreadsort; + +#define DATA_TYPE wstring + +//Pass in an argument to test std::sort +int main(int argc, const char ** argv) { + std::ifstream indata; + std::ofstream outfile; + bool stdSort = false; + unsigned loopCount = 1; + for (int u = 1; u < argc; ++u) { + if (std::string(argv[u]) == "-std") + stdSort = true; + else + loopCount = atoi(argv[u]); + } + double total = 0.0; + //Run multiple loops, if requested + std::vector<DATA_TYPE> array; + for (unsigned u = 0; u < loopCount; ++u) { + indata.open("input.txt", std::ios_base::in | std::ios_base::binary); + if (indata.bad()) { + printf("input.txt could not be opened\n"); + return 1; + } + unsigned short inval; + DATA_TYPE current; + while (indata.good()) { + indata.read(reinterpret_cast<char *>(&inval), sizeof(inval)); + current.push_back(inval); + //32 characters is a moderately long string + if (static_cast<int>(current.size()) > inval || current.size() >= 32) { + array.push_back(current); + current.clear(); + } + } + //adding the last string + if (!current.empty()) + array.push_back(current); + + indata.close(); + clock_t start, end; + double elapsed; + start = clock(); + wchar_t cast_type = 0; + if (stdSort) + //std::sort(&(array[0]), &(array[0]) + uCount); + std::sort(array.begin(), array.end()); + else + //string_sort(&(array[0]), &(array[0]) + uCount, cast_type); + string_sort(array.begin(), array.end(), cast_type); + end = clock(); + elapsed = static_cast<double>(end - start); + if (stdSort) + outfile.open("standard_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + else + outfile.open("boost_sort_out.txt", std::ios_base::out | + std::ios_base::binary | std::ios_base::trunc); + if (outfile.good()) { + for (unsigned u = 0; u < array.size(); ++u){ + for (unsigned v = 0; v < array[u].size(); ++v) + outfile << array[u][v]; + outfile << "\n"; + } + outfile.close(); + } + total += elapsed; + array.clear(); + } + if (stdSort) + printf("std::sort elapsed time %f\n", total / CLOCKS_PER_SEC); + else + printf("spreadsort elapsed time %f\n", total / CLOCKS_PER_SEC); + return 0; +} |