Browse Source

feat: mirror functions in klotski function

master
Dnomd343 2 years ago
parent
commit
f558e18934
  1. 78
      src/klotski_core/ffi/codec.cc
  2. 67
      src/klotski_core/klotski.h
  3. 14
      src/klotski_core/raw_code/convert.cc
  4. 24
      src/klotski_core/raw_code/mirror.cc
  5. 10
      src/klotski_core/raw_code/raw_code.cc
  6. 60
      src/klotski_core/raw_code/raw_code.h

78
src/klotski_core/ffi/codec.cc

@ -10,7 +10,7 @@ using klotski::CommonCode;
using klotski::AllCases;
using klotski::BasicRanges;
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void short_code_enable() {
ShortCode::speed_up(ShortCode::NORMAL);
@ -21,14 +21,22 @@ void short_code_enable_fast() {
}
bool is_short_code_available() {
return BasicRanges::status() == BasicRanges::AVAILABLE;
if (BasicRanges::status() != BasicRanges::AVAILABLE) {
return false;
}
ShortCode::speed_up(ShortCode::NORMAL);
return true;
}
bool is_short_code_available_fast() {
return AllCases::status() == AllCases::AVAILABLE;
if (AllCases::status() != AllCases::AVAILABLE) {
return false;
}
ShortCode::speed_up(ShortCode::FAST);
return true;
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool raw_code_check(uint64_t raw_code) {
return RawCode::check(raw_code);
@ -42,7 +50,7 @@ bool common_code_check(uint64_t common_code) {
return CommonCode::check(common_code);
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool raw_code_to_short_code(uint64_t raw_code, uint32_t *short_code) {
if (!RawCode::check(raw_code)) {
@ -104,7 +112,7 @@ bool common_code_to_short_code(uint64_t common_code, uint32_t *short_code) {
return true;
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
uint32_t raw_code_to_short_code_unsafe(uint64_t raw_code) {
return RawCode::unsafe_create(raw_code)
@ -132,7 +140,59 @@ uint32_t common_code_to_short_code_unsafe(uint64_t common_code) {
return CommonCode::unsafe_create(common_code).to_short_code().unwrap();
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool is_vertical_mirror(uint64_t raw_code, bool *result) {
if (!RawCode::check(raw_code)) {
return false;
}
*result = RawCode::unsafe_create(raw_code).is_vertical_mirror();
return true;
}
bool is_horizontal_mirror(uint64_t raw_code, bool *result) {
if (!RawCode::check(raw_code)) {
return false;
}
*result = RawCode::unsafe_create(raw_code).is_horizontal_mirror();
return true;
}
bool to_vertical_mirror(uint64_t raw_code, uint64_t *result) {
if (!RawCode::check(raw_code)) {
return false;
}
*result = RawCode::unsafe_create(raw_code).to_vertical_mirror().unwrap();
return true;
}
bool to_horizontal_mirror(uint64_t raw_code, uint64_t *result) {
if (!RawCode::check(raw_code)) {
return false;
}
*result = RawCode::unsafe_create(raw_code).to_horizontal_mirror().unwrap();
return true;
}
///////////////////////////////////////////////////////////////////////////////
bool is_vertical_mirror_unsafe(uint64_t raw_code) {
return RawCode::unsafe_create(raw_code).is_vertical_mirror();
}
bool is_horizontal_mirror_unsafe(uint64_t raw_code) {
return RawCode::unsafe_create(raw_code).is_horizontal_mirror();
}
uint64_t to_vertical_mirror_unsafe(uint64_t raw_code) {
return RawCode::unsafe_create(raw_code).to_vertical_mirror().unwrap();
}
uint64_t to_horizontal_mirror_unsafe(uint64_t raw_code) {
return RawCode::unsafe_create(raw_code).to_horizontal_mirror().unwrap();
}
///////////////////////////////////////////////////////////////////////////////
const uint32_t SHORT_CODE_STR_SIZE = 6;
@ -154,7 +214,7 @@ bool short_code_from_string(const char short_code_str[], uint32_t *short_code) {
return true;
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
const uint32_t COMMON_CODE_STR_SIZE = 10;
@ -185,4 +245,4 @@ bool common_code_from_string(const char common_code_str[], uint64_t *common_code
return true;
}
////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////

67
src/klotski_core/klotski.h

@ -7,6 +7,8 @@
#include <stdbool.h>
#endif
#define EXTERN_FUNC extern
/// klotski test interface
#ifdef __cplusplus
extern "C" {
@ -64,38 +66,47 @@ extern "C" {
#ifdef __cplusplus
extern "C" {
#endif
// short code index warm up
extern void short_code_enable();
extern void short_code_enable_fast();
extern bool is_short_code_available();
extern bool is_short_code_available_fast();
extern bool raw_code_check(uint64_t raw_code);
extern bool short_code_check(uint32_t short_code);
extern bool common_code_check(uint64_t common_code);
extern bool raw_code_to_short_code(uint64_t raw_code, uint32_t *short_code);
extern bool short_code_to_raw_code(uint32_t short_code, uint64_t *raw_code);
extern bool raw_code_to_common_code(uint64_t raw_code, uint64_t *common_code);
extern bool common_code_to_raw_code(uint64_t common_code, uint64_t *raw_code);
extern bool short_code_to_common_code(uint32_t short_code, uint64_t *common_code);
extern bool common_code_to_short_code(uint64_t common_code, uint32_t *short_code);
extern uint32_t raw_code_to_short_code_unsafe(uint64_t raw_code);
extern uint64_t short_code_to_raw_code_unsafe(uint32_t short_code);
extern uint64_t raw_code_to_common_code_unsafe(uint64_t raw_code);
extern uint64_t common_code_to_raw_code_unsafe(uint64_t common_code);
extern uint64_t short_code_to_common_code_unsafe(uint32_t short_code);
extern uint32_t common_code_to_short_code_unsafe(uint64_t common_code);
EXTERN_FUNC void short_code_enable();
EXTERN_FUNC void short_code_enable_fast();
EXTERN_FUNC bool is_short_code_available();
EXTERN_FUNC bool is_short_code_available_fast();
EXTERN_FUNC bool raw_code_check(uint64_t raw_code);
EXTERN_FUNC bool short_code_check(uint32_t short_code);
EXTERN_FUNC bool common_code_check(uint64_t common_code);
EXTERN_FUNC bool raw_code_to_short_code(uint64_t raw_code, uint32_t *short_code);
EXTERN_FUNC bool short_code_to_raw_code(uint32_t short_code, uint64_t *raw_code);
EXTERN_FUNC bool raw_code_to_common_code(uint64_t raw_code, uint64_t *common_code);
EXTERN_FUNC bool common_code_to_raw_code(uint64_t common_code, uint64_t *raw_code);
EXTERN_FUNC bool short_code_to_common_code(uint32_t short_code, uint64_t *common_code);
EXTERN_FUNC bool common_code_to_short_code(uint64_t common_code, uint32_t *short_code);
EXTERN_FUNC uint32_t raw_code_to_short_code_unsafe(uint64_t raw_code);
EXTERN_FUNC uint64_t short_code_to_raw_code_unsafe(uint32_t short_code);
EXTERN_FUNC uint64_t raw_code_to_common_code_unsafe(uint64_t raw_code);
EXTERN_FUNC uint64_t common_code_to_raw_code_unsafe(uint64_t common_code);
EXTERN_FUNC uint64_t short_code_to_common_code_unsafe(uint32_t short_code);
EXTERN_FUNC uint32_t common_code_to_short_code_unsafe(uint64_t common_code);
EXTERN_FUNC bool is_vertical_mirror(uint64_t raw_code, bool *result);
EXTERN_FUNC bool is_horizontal_mirror(uint64_t raw_code, bool *result);
EXTERN_FUNC bool to_vertical_mirror(uint64_t raw_code, uint64_t *result);
EXTERN_FUNC bool to_horizontal_mirror(uint64_t raw_code, uint64_t *result);
EXTERN_FUNC bool is_vertical_mirror_unsafe(uint64_t raw_code);
EXTERN_FUNC bool is_horizontal_mirror_unsafe(uint64_t raw_code);
EXTERN_FUNC uint64_t to_vertical_mirror_unsafe(uint64_t raw_code);
EXTERN_FUNC uint64_t to_horizontal_mirror_unsafe(uint64_t raw_code);
extern const uint32_t SHORT_CODE_STR_SIZE;
extern bool short_code_to_string(uint32_t short_code, char short_code_str[]);
extern bool short_code_from_string(const char short_code_str[], uint32_t *short_code);
EXTERN_FUNC bool short_code_to_string(uint32_t short_code, char short_code_str[]);
EXTERN_FUNC bool short_code_from_string(const char short_code_str[], uint32_t *short_code);
extern const uint32_t COMMON_CODE_STR_SIZE;
extern bool common_code_to_string(uint64_t common_code, char common_code_str[]);
extern bool common_code_to_string_shorten(uint64_t common_code, char common_code_str[]);
extern bool common_code_from_string(const char common_code_str[], uint64_t *common_code);
EXTERN_FUNC bool common_code_to_string(uint64_t common_code, char common_code_str[]);
EXTERN_FUNC bool common_code_to_string_shorten(uint64_t common_code, char common_code_str[]);
EXTERN_FUNC bool common_code_from_string(const char common_code_str[], uint64_t *common_code);
#ifdef __cplusplus
}
#endif

14
src/klotski_core/raw_code/convert.cc

@ -7,17 +7,17 @@ using klotski::RawCodeException;
/// -------------------------- RawCode to CommonCode --------------------------
CommonCode RawCode::to_common_code() const {
CommonCode RawCode::to_common_code() const noexcept {
return CommonCode::unsafe_create(RawCode::compact(code));
}
/// -------------------------- CommonCode to RawCode --------------------------
RawCode::RawCode(CommonCode &&common_code) {
RawCode::RawCode(CommonCode &&common_code) noexcept {
code = RawCode::extract(common_code.unwrap()); // convert from common code
}
RawCode::RawCode(const CommonCode &common_code) {
RawCode::RawCode(const CommonCode &common_code) noexcept {
code = RawCode::extract(common_code.unwrap()); // convert from common code
}
@ -25,7 +25,7 @@ RawCode RawCode::from_common_code(uint64_t common_code) {
return RawCode(CommonCode(common_code));
}
RawCode RawCode::from_common_code(CommonCode &&common_code) {
RawCode RawCode::from_common_code(CommonCode &&common_code) noexcept {
return RawCode(std::forward<CommonCode>(common_code));
}
@ -35,7 +35,7 @@ RawCode RawCode::from_common_code(std::string &&common_code) {
));
}
RawCode RawCode::from_common_code(const CommonCode &common_code) {
RawCode RawCode::from_common_code(const CommonCode &common_code) noexcept {
return RawCode(common_code);
}
@ -46,7 +46,7 @@ RawCode RawCode::from_common_code(const std::string &common_code) {
/// ----------------------------- Basic Functions -----------------------------
/// NOTE: ensure that input raw code is valid!
uint64_t RawCode::compact(uint64_t raw_code) { // raw code --> common code
uint64_t RawCode::compact(uint64_t raw_code) noexcept { // raw code --> common code
int unfilled = 16;
uint64_t head = 0; // 2x2 block address
uint32_t range = 0;
@ -75,7 +75,7 @@ uint64_t RawCode::compact(uint64_t raw_code) { // raw code --> common code
}
/// NOTE: ensure that input common code is valid!
uint64_t RawCode::extract(uint64_t common_code) { // common code --> raw code
uint64_t RawCode::extract(uint64_t common_code) noexcept { // common code --> raw code
auto code = C_2x2 << (common_code >> 32) * 3; // flag for 2x2 block
auto range = Common::range_reverse((uint32_t)common_code); // reversed range

24
src/klotski_core/raw_code/mirror.cc

@ -5,37 +5,37 @@ using klotski::RawCode;
/// ----------------------------- Mirror Convert ------------------------------
RawCode RawCode::to_vertical_mirror() const {
RawCode RawCode::to_vertical_mirror() const noexcept {
return RawCode::unsafe_create(vertical_mirror(code));
}
RawCode RawCode::to_horizontal_mirror() const {
RawCode RawCode::to_horizontal_mirror() const noexcept {
return RawCode::unsafe_create(horizontal_mirror(code));
}
/// ------------------------------ Mirror Check -------------------------------
bool RawCode::is_vertical_mirror() const {
bool RawCode::is_vertical_mirror() const noexcept {
return vertical_mirror_check(code);
}
bool RawCode::is_horizontal_mirror() const {
bool RawCode::is_horizontal_mirror() const noexcept {
return horizontal_mirror_check(code);
}
bool RawCode::is_vertical_mirror(RawCode &&raw_code) const {
bool RawCode::is_vertical_mirror(RawCode &&raw_code) const noexcept {
return raw_code.unwrap() == vertical_mirror(code);
}
bool RawCode::is_horizontal_mirror(RawCode &&raw_code) const {
bool RawCode::is_horizontal_mirror(RawCode &&raw_code) const noexcept {
return raw_code.unwrap() == horizontal_mirror(code);
}
bool RawCode::is_vertical_mirror(const RawCode &raw_code) const {
bool RawCode::is_vertical_mirror(const RawCode &raw_code) const noexcept {
return raw_code.unwrap() == vertical_mirror(code);
}
bool RawCode::is_horizontal_mirror(const RawCode &raw_code) const {
bool RawCode::is_horizontal_mirror(const RawCode &raw_code) const noexcept {
return raw_code.unwrap() == horizontal_mirror(code);
}
@ -118,7 +118,7 @@ inline void horizontal_clear(uint64_t &raw_code) {
}
}
uint64_t RawCode::vertical_mirror(uint64_t raw_code) {
uint64_t RawCode::vertical_mirror(uint64_t raw_code) noexcept {
vertical_fill(raw_code);
raw_code = (raw_code & MASK_MIRROR_V3)
| ((raw_code >> 48) & MASK_MIRROR_V1) | ((raw_code >> 24) & MASK_MIRROR_V2)
@ -127,7 +127,7 @@ uint64_t RawCode::vertical_mirror(uint64_t raw_code) {
return raw_code;
}
uint64_t RawCode::horizontal_mirror(uint64_t raw_code) {
uint64_t RawCode::horizontal_mirror(uint64_t raw_code) noexcept {
horizontal_fill(raw_code);
raw_code = ((raw_code >> 9) & MASK_MIRROR_H1) | ((raw_code >> 3) & MASK_MIRROR_H2)
| ((raw_code & MASK_MIRROR_H2) << 3) | ((raw_code & MASK_MIRROR_H1) << 9); // flip raw code
@ -135,13 +135,13 @@ uint64_t RawCode::horizontal_mirror(uint64_t raw_code) {
return raw_code;
}
bool RawCode::vertical_mirror_check(uint64_t raw_code) {
bool RawCode::vertical_mirror_check(uint64_t raw_code) noexcept {
vertical_fill(raw_code);
return !(MASK_MIRROR_V1 & ((raw_code >> 48) ^ raw_code))
&& !(MASK_MIRROR_V2 & ((raw_code >> 24) ^ raw_code));
}
bool RawCode::horizontal_mirror_check(uint64_t raw_code) {
bool RawCode::horizontal_mirror_check(uint64_t raw_code) noexcept {
horizontal_fill(raw_code);
return !(MASK_MIRROR_H1 & ((raw_code >> 9) ^ raw_code))
&& !(MASK_MIRROR_H2 & ((raw_code >> 3) ^ raw_code));

10
src/klotski_core/raw_code/raw_code.cc

@ -20,11 +20,11 @@ namespace std {
}
namespace klotski {
bool RawCode::operator==(const RawCode &raw_code) const {
bool RawCode::operator==(const RawCode &raw_code) const noexcept {
return this->code == raw_code.code;
}
bool RawCode::operator!=(const RawCode &raw_code) const {
bool RawCode::operator!=(const RawCode &raw_code) const noexcept {
return this->code != raw_code.code;
}
@ -45,7 +45,7 @@ namespace klotski {
}
namespace klotski {
bool RawCode::valid() const {
bool RawCode::valid() const noexcept {
return RawCode::check(code);
}
@ -53,7 +53,7 @@ namespace klotski {
return RawCode(raw_code);
}
RawCode RawCode::unsafe_create(uint64_t raw_code) { // create without check
RawCode RawCode::unsafe_create(uint64_t raw_code) noexcept { // create without check
auto tmp = RawCode(); // init directly
tmp.code = raw_code;
return tmp;
@ -67,7 +67,7 @@ namespace klotski {
}
}
bool RawCode::check(uint64_t raw_code) { // check whether raw code is valid
bool RawCode::check(uint64_t raw_code) noexcept { // check whether raw code is valid
/// MASK_1x1 | MASK_1x2 | MASK_2x1 | MASK_2x2
/// 100 000 000 000 | 000 100 000 000 | 000 000 000 000 | 000 100 000 000
/// 000 000 000 000 | 000 000 000 000 | 100 000 000 000 | 100 100 000 000

60
src/klotski_core/raw_code/raw_code.h

@ -57,60 +57,60 @@ namespace klotski {
uint64_t code;
RawCode() = default; // unsafe initialize
static inline uint64_t compact(uint64_t raw_code); // raw code -> common code
static inline uint64_t extract(uint64_t common_code); // common code -> raw code
static inline uint64_t compact(uint64_t raw_code) noexcept; // raw code -> common code
static inline uint64_t extract(uint64_t common_code) noexcept; // common code -> raw code
static inline uint64_t vertical_mirror(uint64_t raw_code); // to vertical mirror
static inline uint64_t horizontal_mirror(uint64_t raw_code); // to horizontal mirror
static inline uint64_t vertical_mirror(uint64_t raw_code) noexcept; // to vertical mirror
static inline uint64_t horizontal_mirror(uint64_t raw_code) noexcept; // to horizontal mirror
static inline bool vertical_mirror_check(uint64_t raw_code); // check vertical mirror
static inline bool horizontal_mirror_check(uint64_t raw_code); // check horizontal mirror
static inline bool vertical_mirror_check(uint64_t raw_code) noexcept; // check vertical mirror
static inline bool horizontal_mirror_check(uint64_t raw_code) noexcept; // check horizontal mirror
public:
/// RawCode validity check
bool valid() const;
static bool check(uint64_t raw_code);
bool valid() const noexcept;
static bool check(uint64_t raw_code) noexcept;
/// Operators of RawCode
bool operator==(const RawCode &raw_code) const;
bool operator!=(const RawCode &raw_code) const;
constexpr explicit operator uint64_t() const { return code; }
bool operator==(const RawCode &raw_code) const noexcept;
bool operator!=(const RawCode &raw_code) const noexcept;
constexpr explicit operator uint64_t() const noexcept { return code; }
friend std::ostream& operator<<(std::ostream &out, const RawCode &self);
/// Export functions
CommonCode to_common_code() const;
constexpr uint64_t unwrap() const { return code; }
CommonCode to_common_code() const noexcept;
constexpr uint64_t unwrap() const noexcept { return code; }
/// RawCode constructors
explicit RawCode(uint64_t raw_code);
explicit RawCode(CommonCode &&common_code);
explicit RawCode(const CommonCode &common_code);
explicit RawCode(CommonCode &&common_code) noexcept;
explicit RawCode(const CommonCode &common_code) noexcept;
/// Static initialization
static RawCode create(uint64_t raw_code);
static RawCode unsafe_create(uint64_t raw_code);
static RawCode unsafe_create(uint64_t raw_code) noexcept;
static RawCode from_common_code(uint64_t common_code);
static RawCode from_common_code(CommonCode &&common_code);
static RawCode from_common_code(CommonCode &&common_code) noexcept;
static RawCode from_common_code(std::string &&common_code);
static RawCode from_common_code(const CommonCode &common_code);
static RawCode from_common_code(const CommonCode &common_code) noexcept;
static RawCode from_common_code(const std::string &common_code);
/// Mirror functions
RawCode to_vertical_mirror() const;
RawCode to_horizontal_mirror() const;
RawCode to_vertical_mirror() const noexcept;
RawCode to_horizontal_mirror() const noexcept;
bool is_vertical_mirror() const; // whether vertically symmetrical
bool is_horizontal_mirror() const; // whether horizontally symmetrical
bool is_vertical_mirror() const noexcept; // whether vertically symmetrical
bool is_horizontal_mirror() const noexcept; // whether horizontally symmetrical
bool is_vertical_mirror(RawCode &&raw_code) const; // whether vertically symmetric to another
bool is_vertical_mirror(const RawCode &raw_code) const;
bool is_horizontal_mirror(RawCode &&raw_code) const; // whether horizontally symmetric to another
bool is_horizontal_mirror(const RawCode &raw_code) const;
bool is_vertical_mirror(RawCode &&raw_code) const noexcept; // whether vertically symmetric to another
bool is_vertical_mirror(const RawCode &raw_code) const noexcept;
bool is_horizontal_mirror(RawCode &&raw_code) const noexcept; // whether horizontally symmetric to another
bool is_horizontal_mirror(const RawCode &raw_code) const noexcept;
};
inline bool operator==(uint64_t r1, const RawCode &r2) { return r1 == r2.unwrap(); }
inline bool operator!=(uint64_t r1, const RawCode &r2) { return r1 != r2.unwrap(); }
inline bool operator==(const RawCode &r1, uint64_t r2) { return r1.unwrap() == r2; }
inline bool operator!=(const RawCode &r1, uint64_t r2) { return r1.unwrap() != r2; }
inline bool operator==(uint64_t r1, const RawCode &r2) noexcept { return r1 == r2.unwrap(); }
inline bool operator!=(uint64_t r1, const RawCode &r2) noexcept { return r1 != r2.unwrap(); }
inline bool operator==(const RawCode &r1, uint64_t r2) noexcept { return r1.unwrap() == r2; }
inline bool operator!=(const RawCode &r1, uint64_t r2) noexcept { return r1.unwrap() != r2; }
}

Loading…
Cancel
Save