From 2c7ff2425df53f5d0a7a3d114e245599f1db747b Mon Sep 17 00:00:00 2001 From: Dnomd343 Date: Sat, 8 Apr 2023 18:38:03 +0800 Subject: [PATCH] update: Benchmark module --- src/klotski_core/benchmark/benchmark.cc | 102 +++++++++++------------ src/klotski_core/benchmark/benchmark.h | 104 ++++++++++++------------ src/klotski_core/benchmark/chore.cc | 68 ++++++++-------- 3 files changed, 138 insertions(+), 136 deletions(-) diff --git a/src/klotski_core/benchmark/benchmark.cc b/src/klotski_core/benchmark/benchmark.cc index afa2f1a..4a6cd35 100644 --- a/src/klotski_core/benchmark/benchmark.cc +++ b/src/klotski_core/benchmark/benchmark.cc @@ -40,36 +40,36 @@ double Benchmark::all_cases(TIME format) noexcept { /// -------------------------- Benchmark Code Check --------------------------- double Benchmark::raw_code_check(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.valid(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } double Benchmark::short_code_check(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&short_code : all_short_codes) { + for (auto &&short_code : all_short_codes_) { short_code.valid(); } - return time_format(start, format) / (double)all_short_codes.size(); + return time_format(start, format) / (double)all_short_codes_.size(); } double Benchmark::common_code_check(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&common_code : all_common_codes) { + for (auto &&common_code : all_common_codes_) { common_code.valid(); } - return time_format(start, format) / (double)all_common_codes.size(); + return time_format(start, format) / (double)all_common_codes_.size(); } double Benchmark::raw_code_check_random(TIME format) noexcept { @@ -108,167 +108,167 @@ double Benchmark::common_code_check_random(TIME format) noexcept { /// -------------------------- Benchmark Code String -------------------------- double Benchmark::short_code_to_string(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&short_code : all_short_codes) { + for (auto &&short_code : all_short_codes_) { short_code.to_string(); } - return time_format(start, format) / (double)all_short_codes.size(); + return time_format(start, format) / (double)all_short_codes_.size(); } double Benchmark::short_code_from_string(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&short_code : all_short_codes_str) { + for (auto &&short_code : all_short_codes_str_) { ShortCode{std::forward(short_code)}; } - return time_format(start, format) / (double)all_short_codes_str.size(); + return time_format(start, format) / (double)all_short_codes_str_.size(); } double Benchmark::common_code_to_string(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&common_code : all_common_codes) { + for (auto &&common_code : all_common_codes_) { common_code.to_string(); } - return time_format(start, format) / (double)all_common_codes.size(); + return time_format(start, format) / (double)all_common_codes_.size(); } double Benchmark::common_code_from_string(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&common_code : all_common_codes_str) { + for (auto &&common_code : all_common_codes_str_) { CommonCode{std::forward(common_code)}; } - return time_format(start, format) / (double)all_common_codes_str.size(); + return time_format(start, format) / (double)all_common_codes_str_.size(); } /// ------------------------- Benchmark Code Convert -------------------------- double Benchmark::common_code_to_raw_code(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&common_code : all_common_codes) { + for (auto &&common_code : all_common_codes_) { RawCode{std::forward(common_code)}; } - return time_format(start, format) / (double)all_common_codes.size(); + return time_format(start, format) / (double)all_common_codes_.size(); } double Benchmark::raw_code_to_common_code(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.to_common_code(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } double Benchmark::common_code_to_short_code(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } uint32_t num = 0; ShortCode::speed_up(ShortCode::NORMAL); auto start = clock(); - for (uint64_t i = 0; i < all_common_codes.size(); i += 1000) { - ShortCode{all_common_codes[i]}; + for (uint64_t i = 0; i < all_common_codes_.size(); i += 1000) { + ShortCode{all_common_codes_[i]}; ++num; } return time_format(start, format) / (double)num; } double Benchmark::short_code_to_common_code(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } uint32_t num = 0; ShortCode::speed_up(ShortCode::NORMAL); auto start = clock(); - for (uint64_t i = 0; i < all_short_codes.size(); i += 1000) { - all_short_codes[i].to_common_code(); + for (uint64_t i = 0; i < all_short_codes_.size(); i += 1000) { + all_short_codes_[i].to_common_code(); ++num; } return time_format(start, format) / (double)num; } double Benchmark::common_code_to_short_code_fast(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } ShortCode::speed_up(ShortCode::FAST); auto start = clock(); - for (auto &&common_code : all_common_codes) { + for (auto &&common_code : all_common_codes_) { ShortCode{std::forward(common_code)}; } - return time_format(start, format) / (double)all_common_codes.size(); + return time_format(start, format) / (double)all_common_codes_.size(); } double Benchmark::short_code_to_common_code_fast(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } ShortCode::speed_up(ShortCode::FAST); auto start = clock(); - for (auto &&short_code : all_short_codes) { + for (auto &&short_code : all_short_codes_) { short_code.to_common_code(); } - return time_format(start, format) / (double)all_short_codes.size(); + return time_format(start, format) / (double)all_short_codes_.size(); } /// ---------------------------- Benchmark Mirror ----------------------------- double Benchmark::vertical_mirror_check(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.is_vertical_mirror(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } double Benchmark::horizontal_mirror_check(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.is_horizontal_mirror(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } double Benchmark::vertical_mirror_convert(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.to_vertical_mirror(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } double Benchmark::horizontal_mirror_convert(TIME format) noexcept { - if (!data_ready) { + if (!data_ready_) { return -1; // data no ready -> skip } auto start = clock(); - for (auto &&raw_code : all_raw_codes) { + for (auto &&raw_code : all_raw_codes_) { raw_code.to_horizontal_mirror(); } - return time_format(start, format) / (double)all_raw_codes.size(); + return time_format(start, format) / (double)all_raw_codes_.size(); } diff --git a/src/klotski_core/benchmark/benchmark.h b/src/klotski_core/benchmark/benchmark.h index b7036aa..f9d2782 100644 --- a/src/klotski_core/benchmark/benchmark.h +++ b/src/klotski_core/benchmark/benchmark.h @@ -27,55 +27,57 @@ #include "common_code.h" namespace klotski { - class Benchmark { - public: - enum TIME { - S, MS, US, NS - }; - static void data_preparation() noexcept; - static double warm_up(uint64_t count) noexcept; - static double range_flip(TIME format = NS) noexcept; - - static double all_cases(TIME format = MS) noexcept; - static double basic_ranges(TIME format = MS) noexcept; - - static double raw_code_check(TIME format = NS) noexcept; - static double short_code_check(TIME format = NS) noexcept; - static double common_code_check(TIME format = NS) noexcept; - static double raw_code_check_random(TIME format = NS) noexcept; - static double short_code_check_random(TIME format = NS) noexcept; - static double common_code_check_random(TIME format = NS) noexcept; - - static double short_code_to_string(TIME format = NS) noexcept; - static double short_code_from_string(TIME format = NS) noexcept; - static double common_code_to_string(TIME format = NS) noexcept; - static double common_code_from_string(TIME format = NS) noexcept; - - static double common_code_to_raw_code(TIME format = NS) noexcept; - static double raw_code_to_common_code(TIME format = NS) noexcept; - static double common_code_to_short_code(TIME format = US) noexcept; - static double short_code_to_common_code(TIME format = US) noexcept; - static double common_code_to_short_code_fast(TIME format = NS) noexcept; - static double short_code_to_common_code_fast(TIME format = NS) noexcept; - - static double vertical_mirror_check(TIME format = NS) noexcept; - static double horizontal_mirror_check(TIME format = NS) noexcept; - static double vertical_mirror_convert(TIME format = NS) noexcept; - static double horizontal_mirror_convert(TIME format = NS) noexcept; - - private: - static bool data_ready; - static std::mutex data_building; - static std::vector all_raw_codes; - static std::vector all_short_codes; - static std::vector all_common_codes; - static std::vector all_short_codes_str; - static std::vector all_common_codes_str; - - static void build_data() noexcept; - static uint32_t random_seed() noexcept; - static double time_format(clock_t start, TIME format) noexcept; - static std::vector generate_u32_rand(uint32_t count) noexcept; - static std::vector generate_u64_rand(uint32_t count) noexcept; + +class Benchmark { +public: + enum TIME { + S, MS, US, NS }; -} + static void data_initialize() noexcept; + static double warm_up(uint64_t count) noexcept; + static double range_flip(TIME format = NS) noexcept; + + static double all_cases(TIME format = MS) noexcept; + static double basic_ranges(TIME format = MS) noexcept; + + static double raw_code_check(TIME format = NS) noexcept; + static double short_code_check(TIME format = NS) noexcept; + static double common_code_check(TIME format = NS) noexcept; + static double raw_code_check_random(TIME format = NS) noexcept; + static double short_code_check_random(TIME format = NS) noexcept; + static double common_code_check_random(TIME format = NS) noexcept; + + static double short_code_to_string(TIME format = NS) noexcept; + static double short_code_from_string(TIME format = NS) noexcept; + static double common_code_to_string(TIME format = NS) noexcept; + static double common_code_from_string(TIME format = NS) noexcept; + + static double common_code_to_raw_code(TIME format = NS) noexcept; + static double raw_code_to_common_code(TIME format = NS) noexcept; + static double common_code_to_short_code(TIME format = US) noexcept; + static double short_code_to_common_code(TIME format = US) noexcept; + static double common_code_to_short_code_fast(TIME format = NS) noexcept; + static double short_code_to_common_code_fast(TIME format = NS) noexcept; + + static double vertical_mirror_check(TIME format = NS) noexcept; + static double horizontal_mirror_check(TIME format = NS) noexcept; + static double vertical_mirror_convert(TIME format = NS) noexcept; + static double horizontal_mirror_convert(TIME format = NS) noexcept; + +private: + static bool data_ready_; + static std::mutex data_building_; + static std::vector all_raw_codes_; + static std::vector all_short_codes_; + static std::vector all_common_codes_; + static std::vector all_short_codes_str_; + static std::vector all_common_codes_str_; + + static void build_data() noexcept; + static uint32_t random_seed() noexcept; + static double time_format(clock_t start, TIME format) noexcept; + static std::vector generate_u32_rand(uint32_t count) noexcept; + static std::vector generate_u64_rand(uint32_t count) noexcept; +}; + +} // namespace klotski diff --git a/src/klotski_core/benchmark/chore.cc b/src/klotski_core/benchmark/chore.cc index 2226d7a..a70533a 100644 --- a/src/klotski_core/benchmark/chore.cc +++ b/src/klotski_core/benchmark/chore.cc @@ -2,18 +2,15 @@ #include #include "benchmark.h" -using klotski::RawCode; -using klotski::ShortCode; -using klotski::CommonCode; -using klotski::Benchmark; - -bool Benchmark::data_ready = false; -std::mutex Benchmark::data_building; -std::vector Benchmark::all_raw_codes; -std::vector Benchmark::all_short_codes; -std::vector Benchmark::all_common_codes; -std::vector Benchmark::all_short_codes_str; -std::vector Benchmark::all_common_codes_str; +namespace klotski { + +bool Benchmark::data_ready_ = false; +std::mutex Benchmark::data_building_; +std::vector Benchmark::all_raw_codes_; +std::vector Benchmark::all_short_codes_; +std::vector Benchmark::all_common_codes_; +std::vector Benchmark::all_short_codes_str_; +std::vector Benchmark::all_common_codes_str_; uint32_t Benchmark::random_seed() noexcept { using namespace std::chrono; @@ -47,6 +44,7 @@ double Benchmark::time_format(clock_t start, TIME format) noexcept { return time / CLOCKS_PER_SEC; } +/// Generate a specified count of 32-bit random numbers. std::vector Benchmark::generate_u32_rand(uint32_t count) noexcept { std::vector result; result.reserve(count); @@ -56,71 +54,73 @@ std::vector Benchmark::generate_u32_rand(uint32_t count) noexcept { std::srand(seed); for (uint32_t i = 0; i < count; ++i) { - auto tmp = high_bit | static_cast(std::rand()); + auto tmp = high_bit | static_cast(std::rand()); // int32_t -> uint32_t result.emplace_back(tmp); high_bit = tmp << 31; } return result; } +/// Generate a specified count of 64-bit random numbers. std::vector Benchmark::generate_u64_rand(uint32_t count) noexcept { std::vector result; result.reserve(count); - auto tmp = generate_u32_rand(count * 2); for (uint32_t i = 0; i < count; ++i) { - result.emplace_back((uint64_t)tmp[i * 2] << 32 | tmp[i * 2 + 1]); + result.emplace_back((uint64_t)tmp[i * 2] << 32 | tmp[i * 2 + 1]); // combine two uint32_t } return result; } -void Benchmark::data_preparation() noexcept { - if (!Benchmark::data_ready) { - if (Benchmark::data_building.try_lock()) { // mutex lock success +void Benchmark::data_initialize() noexcept { + if (!data_ready_) { + if (data_building_.try_lock()) { // mutex lock success build_data(); // start build process - Benchmark::data_ready = true; // set available flag + data_ready_ = true; } else { - Benchmark::data_building.lock(); // blocking waiting + data_building_.lock(); // blocking waiting } - Benchmark::data_building.unlock(); // release mutex + data_building_.unlock(); // release mutex } } void Benchmark::build_data() noexcept { /// short code data preparation - std::vector tmp(klotski::SHORT_CODE_LIMIT); + std::vector tmp(SHORT_CODE_LIMIT); std::iota(tmp.begin(), tmp.end(), 0); - all_short_codes.reserve(klotski::SHORT_CODE_LIMIT); + all_short_codes_.reserve(SHORT_CODE_LIMIT); for (auto &&short_code : tmp) { // 0 ~ (SHORT_CODE_LIMIT - 1) - all_short_codes.emplace_back(ShortCode::unsafe_create(short_code)); + all_short_codes_.emplace_back(ShortCode::unsafe_create(short_code)); } - all_short_codes_str.reserve(klotski::SHORT_CODE_LIMIT); + all_short_codes_str_.reserve(SHORT_CODE_LIMIT); for (auto &&short_code : tmp) { // 0 ~ (SHORT_CODE_LIMIT - 1) - all_short_codes_str.emplace_back( + all_short_codes_str_.emplace_back( ShortCode::unsafe_create(short_code).to_string() ); } /// common code info preparation - all_common_codes.reserve(klotski::ALL_CASES_SIZE_SUM); + all_common_codes_.reserve(ALL_CASES_SIZE_SUM); for (uint64_t head = 0; head < 16; ++head) { for (const auto &range : AllCases::fetch()[head]) { - all_common_codes.emplace_back( + all_common_codes_.emplace_back( CommonCode::unsafe_create(head << 32 | range) ); } } - all_common_codes_str.reserve(klotski::ALL_CASES_SIZE_SUM); - for (auto &&common_code : all_common_codes) { - all_common_codes_str.emplace_back(common_code.to_string()); + all_common_codes_str_.reserve(ALL_CASES_SIZE_SUM); + for (auto &&common_code : all_common_codes_) { + all_common_codes_str_.emplace_back(common_code.to_string()); } /// raw code data preparation - all_raw_codes.reserve(klotski::ALL_CASES_SIZE_SUM); - for (auto &&common_code : all_common_codes) { - all_raw_codes.emplace_back(common_code.to_raw_code()); + all_raw_codes_.reserve(ALL_CASES_SIZE_SUM); + for (auto &&common_code : all_common_codes_) { + all_raw_codes_.emplace_back(common_code.to_raw_code()); } } + +} // namespace klotski