|
@ -8,13 +8,14 @@ |
|
|
#define SHOULD_PANIC(FUNC) \ |
|
|
#define SHOULD_PANIC(FUNC) \ |
|
|
try { \ |
|
|
try { \ |
|
|
FUNC; EXPECT_STREQ("should panic", "but no panic"); \ |
|
|
FUNC; EXPECT_STREQ("should panic", "but no panic"); \ |
|
|
} catch (...) {} |
|
|
} catch (klotski::ShortCodeExp&) {} |
|
|
|
|
|
|
|
|
using klotski::AllCases; |
|
|
using klotski::AllCases; |
|
|
using klotski::ShortCode; |
|
|
using klotski::ShortCode; |
|
|
using klotski::CommonCode; |
|
|
using klotski::CommonCode; |
|
|
using klotski::BasicRanges; |
|
|
using klotski::BasicRanges; |
|
|
|
|
|
|
|
|
|
|
|
using klotski::ALL_CASES_SIZE; |
|
|
using klotski::SHORT_CODE_LIMIT; |
|
|
using klotski::SHORT_CODE_LIMIT; |
|
|
using klotski::ALL_CASES_SIZE_SUM; |
|
|
using klotski::ALL_CASES_SIZE_SUM; |
|
|
|
|
|
|
|
@ -33,6 +34,8 @@ TEST(ShortCode, hash) { |
|
|
TEST(ShortCode, validity) { |
|
|
TEST(ShortCode, validity) { |
|
|
EXPECT_NE(ShortCode::check(-1), true); // out of short code range
|
|
|
EXPECT_NE(ShortCode::check(-1), true); // out of short code range
|
|
|
EXPECT_NE(ShortCode::check(29670987), true); // out of short code range
|
|
|
EXPECT_NE(ShortCode::check(29670987), true); // out of short code range
|
|
|
|
|
|
|
|
|
|
|
|
SHOULD_PANIC(ShortCode::create(SHORT_CODE_LIMIT)) // invalid code
|
|
|
SHOULD_PANIC(ShortCode::from_string("R50EH")) // with invalid `0`
|
|
|
SHOULD_PANIC(ShortCode::from_string("R50EH")) // with invalid `0`
|
|
|
SHOULD_PANIC(ShortCode::from_string("123456")) // length != 5
|
|
|
SHOULD_PANIC(ShortCode::from_string("123456")) // length != 5
|
|
|
SHOULD_PANIC(ShortCode::from_string("Z9EFV")) // out of short code range
|
|
|
SHOULD_PANIC(ShortCode::from_string("Z9EFV")) // out of short code range
|
|
@ -67,26 +70,24 @@ TEST(ShortCode, speed_up) { |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
TEST(ShortCode, code_verify) { // test all layout
|
|
|
TEST(ShortCode, code_verify) { // test all layout
|
|
|
std::thread threads[16]; |
|
|
|
|
|
auto test = [](uint64_t head) { |
|
|
auto test = [](uint64_t head) { |
|
|
for (const auto &range : AllCases::fetch()[head]) { |
|
|
for (const auto &range : AllCases::fetch()[head]) { |
|
|
auto code = (uint32_t)ShortCode::from_common_code(head << 32 | range); |
|
|
auto code = (uint32_t)ShortCode::from_common_code(head << 32 | range); |
|
|
EXPECT_EQ(ShortCode::check(code), true); // test static `check` interface
|
|
|
EXPECT_EQ(ShortCode::check(code), true); // test static `check` interface
|
|
|
auto tmp = ShortCode::unsafe_create(code); // test dynamic `valid` interface
|
|
|
auto tmp = ShortCode::unsafe_create(code); |
|
|
EXPECT_EQ(tmp.valid(), true); |
|
|
EXPECT_EQ(tmp.valid(), true); // test dynamic `valid` interface
|
|
|
} |
|
|
} |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
std::thread threads[16]; |
|
|
|
|
|
ShortCode::speed_up(ShortCode::FAST); |
|
|
for (uint64_t head = 0; head < 16; ++head) { // split into 16 threads
|
|
|
for (uint64_t head = 0; head < 16; ++head) { // split into 16 threads
|
|
|
/// NOTE: ensure that short code fast mode enabled
|
|
|
|
|
|
threads[head] = std::thread(test, head); |
|
|
threads[head] = std::thread(test, head); |
|
|
} |
|
|
} |
|
|
for (auto &t : threads) { |
|
|
for (auto &t : threads) { t.join(); } |
|
|
t.join(); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
TEST(ShortCode, code_string) { // test all string code
|
|
|
TEST(ShortCode, code_string) { // test all string code
|
|
|
std::thread threads[16]; |
|
|
|
|
|
auto test = [](uint64_t head) { |
|
|
auto test = [](uint64_t head) { |
|
|
for (const auto &range : AllCases::fetch()[head]) { |
|
|
for (const auto &range : AllCases::fetch()[head]) { |
|
|
std::string code_str; |
|
|
std::string code_str; |
|
@ -105,12 +106,12 @@ TEST(ShortCode, code_string) { // test all string code |
|
|
EXPECT_EQ(ShortCode::from_string(code_str), short_code); // test lower cases
|
|
|
EXPECT_EQ(ShortCode::from_string(code_str), short_code); // test lower cases
|
|
|
} |
|
|
} |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
std::thread threads[16]; |
|
|
for (uint64_t head = 0; head < 16; ++head) { // split into 16 threads
|
|
|
for (uint64_t head = 0; head < 16; ++head) { // split into 16 threads
|
|
|
threads[head] = std::thread(test, head); |
|
|
threads[head] = std::thread(test, head); |
|
|
} |
|
|
} |
|
|
for (auto &t : threads) { |
|
|
for (auto &t : threads) { t.join(); } |
|
|
t.join(); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
TEST(ShortCode, operators) { |
|
|
TEST(ShortCode, operators) { |
|
@ -126,6 +127,9 @@ TEST(ShortCode, operators) { |
|
|
EXPECT_NE(TEST_CODE + 1, ShortCode(TEST_CODE)); // uint32_t != ShortCode
|
|
|
EXPECT_NE(TEST_CODE + 1, ShortCode(TEST_CODE)); // uint32_t != ShortCode
|
|
|
EXPECT_NE(ShortCode(TEST_CODE), TEST_CODE + 1); // ShortCode != uint32_t
|
|
|
EXPECT_NE(ShortCode(TEST_CODE), TEST_CODE + 1); // ShortCode != uint32_t
|
|
|
EXPECT_NE(ShortCode(TEST_CODE), ShortCode::unsafe_create(TEST_CODE + 1)); // ShortCode != ShortCode
|
|
|
EXPECT_NE(ShortCode(TEST_CODE), ShortCode::unsafe_create(TEST_CODE + 1)); // ShortCode != ShortCode
|
|
|
|
|
|
|
|
|
|
|
|
EXPECT_LT(ShortCode(TEST_CODE), ShortCode::unsafe_create(TEST_CODE + 1)); // ShortCode < ShortCode
|
|
|
|
|
|
EXPECT_GT(ShortCode::unsafe_create(TEST_CODE + 1), ShortCode(TEST_CODE)); // ShortCode > ShortCode
|
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
TEST(ShortCode, code_convert) { |
|
|
TEST(ShortCode, code_convert) { |
|
@ -135,6 +139,28 @@ TEST(ShortCode, code_convert) { |
|
|
EXPECT_EQ(ShortCode(TEST_CODE).unwrap(), TEST_CODE); |
|
|
EXPECT_EQ(ShortCode(TEST_CODE).unwrap(), TEST_CODE); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
TEST(ShortCode, batch_convert) { |
|
|
|
|
|
auto test = [](uint64_t head) { |
|
|
|
|
|
std::vector<ShortCode> short_codes; |
|
|
|
|
|
std::vector<CommonCode> common_codes; |
|
|
|
|
|
short_codes.reserve(ALL_CASES_SIZE[head]); |
|
|
|
|
|
common_codes.reserve(ALL_CASES_SIZE[head]); |
|
|
|
|
|
|
|
|
|
|
|
for (auto &&range : AllCases::fetch()[head]) { |
|
|
|
|
|
common_codes.emplace_back(head << 32 | range); |
|
|
|
|
|
short_codes.emplace_back(common_codes.back()); |
|
|
|
|
|
} |
|
|
|
|
|
EXPECT_EQ(short_codes, ShortCode::convert(common_codes)); |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
std::thread threads[16]; |
|
|
|
|
|
ShortCode::speed_up(ShortCode::FAST); |
|
|
|
|
|
for (uint64_t head = 0; head < 16; ++head) { |
|
|
|
|
|
threads[head] = std::thread(test, head); |
|
|
|
|
|
} |
|
|
|
|
|
for (auto &t : threads) { t.join(); } |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
TEST(ShortCode, constructors) { |
|
|
TEST(ShortCode, constructors) { |
|
|
EXPECT_EQ(ShortCode(TEST_CODE).unwrap(), TEST_CODE); |
|
|
EXPECT_EQ(ShortCode(TEST_CODE).unwrap(), TEST_CODE); |
|
|
|
|
|
|
|
|