22
This commit is contained in:
parent
18583a1f58
commit
f073d2d826
43
2019/22.cpp
43
2019/22.cpp
|
@ -4,9 +4,9 @@
|
||||||
#include <variant>
|
#include <variant>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include <gmpxx.h>
|
|
||||||
|
|
||||||
#include <aocpp/Startup.hpp>
|
#include <aocpp/Startup.hpp>
|
||||||
|
#include <zmod.hpp>
|
||||||
|
using namespace zmod;
|
||||||
using namespace aocpp;
|
using namespace aocpp;
|
||||||
|
|
||||||
template <class... Ts> struct overloaded : Ts... { using Ts::operator()...; };
|
template <class... Ts> struct overloaded : Ts... { using Ts::operator()...; };
|
||||||
|
@ -14,45 +14,6 @@ template <class... Ts> overloaded(Ts...) -> overloaded<Ts...>;
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
template <unsigned long Mod>
|
|
||||||
class ZMod {
|
|
||||||
mpz_class value;
|
|
||||||
|
|
||||||
public:
|
|
||||||
ZMod() : value {} {}
|
|
||||||
ZMod(long value) : ZMod{mpz_class{value}} {}
|
|
||||||
ZMod(mpz_class value) {
|
|
||||||
mpz_mod_ui(this->value.get_mpz_t(), value.get_mpz_t(), Mod);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto operator+(ZMod const& rhs) const -> ZMod {
|
|
||||||
return {value + rhs.value};
|
|
||||||
}
|
|
||||||
|
|
||||||
auto operator-() const -> ZMod {
|
|
||||||
return {-value};
|
|
||||||
}
|
|
||||||
|
|
||||||
auto operator-(ZMod const& rhs) const -> ZMod {
|
|
||||||
return {value - rhs.value};
|
|
||||||
}
|
|
||||||
|
|
||||||
auto operator*(ZMod const& rhs) const -> ZMod {
|
|
||||||
return {value * rhs.value};
|
|
||||||
}
|
|
||||||
|
|
||||||
auto inverse() const -> ZMod {
|
|
||||||
mpz_class m{Mod};
|
|
||||||
ZMod result;
|
|
||||||
mpz_invert(result.value.get_mpz_t(), value.get_mpz_t(), m.get_mpz_t());
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto friend operator<<(std::ostream & out, ZMod<Mod> const& x) -> std::ostream & {
|
|
||||||
return out << x.value.get_ui();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Rep>
|
template <typename Rep>
|
||||||
struct LinearFunction {
|
struct LinearFunction {
|
||||||
Rep scale;
|
Rep scale;
|
||||||
|
|
|
@ -50,7 +50,7 @@ add_executable(20 20.cpp)
|
||||||
target_link_libraries(20 aocpp)
|
target_link_libraries(20 aocpp)
|
||||||
|
|
||||||
add_executable(22 22.cpp)
|
add_executable(22 22.cpp)
|
||||||
target_link_libraries(22 aocpp PkgConfig::GMP)
|
target_link_libraries(22 aocpp zmod)
|
||||||
|
|
||||||
add_executable(23 23.cpp)
|
add_executable(23 23.cpp)
|
||||||
target_link_libraries(23 aocpp intcode)
|
target_link_libraries(23 aocpp intcode)
|
||||||
|
|
|
@ -18,5 +18,6 @@ find_package(PkgConfig)
|
||||||
pkg_check_modules(GMP REQUIRED IMPORTED_TARGET gmp)
|
pkg_check_modules(GMP REQUIRED IMPORTED_TARGET gmp)
|
||||||
|
|
||||||
add_subdirectory(lib)
|
add_subdirectory(lib)
|
||||||
|
add_subdirectory(zmod)
|
||||||
add_subdirectory(intcode)
|
add_subdirectory(intcode)
|
||||||
add_subdirectory(2019)
|
add_subdirectory(2019)
|
||||||
|
|
3
zmod/CMakeLists.txt
Normal file
3
zmod/CMakeLists.txt
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
add_library(zmod INTERFACE)
|
||||||
|
target_link_libraries(zmod PkgConfig::GMP)
|
||||||
|
target_include_directories(zmod PUBLIC include)
|
50
zmod/include/zmod.hpp
Normal file
50
zmod/include/zmod.hpp
Normal file
|
@ -0,0 +1,50 @@
|
||||||
|
#ifndef ZMOD_HPP_
|
||||||
|
#define ZMOD_HPP_
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
|
#include <gmpxx.h>
|
||||||
|
|
||||||
|
namespace zmod {
|
||||||
|
|
||||||
|
template <unsigned long Mod>
|
||||||
|
class ZMod {
|
||||||
|
mpz_class value;
|
||||||
|
|
||||||
|
public:
|
||||||
|
ZMod() : value {} {}
|
||||||
|
ZMod(long value) : ZMod{mpz_class{value}} {}
|
||||||
|
ZMod(mpz_class value) {
|
||||||
|
mpz_mod_ui(this->value.get_mpz_t(), value.get_mpz_t(), Mod);
|
||||||
|
}
|
||||||
|
|
||||||
|
auto operator+(ZMod const& rhs) const -> ZMod {
|
||||||
|
return {value + rhs.value};
|
||||||
|
}
|
||||||
|
|
||||||
|
auto operator-() const -> ZMod {
|
||||||
|
return {-value};
|
||||||
|
}
|
||||||
|
|
||||||
|
auto operator-(ZMod const& rhs) const -> ZMod {
|
||||||
|
return {value - rhs.value};
|
||||||
|
}
|
||||||
|
|
||||||
|
auto operator*(ZMod const& rhs) const -> ZMod {
|
||||||
|
return {value * rhs.value};
|
||||||
|
}
|
||||||
|
|
||||||
|
auto inverse() const -> ZMod {
|
||||||
|
mpz_class m{Mod};
|
||||||
|
ZMod result;
|
||||||
|
mpz_invert(result.value.get_mpz_t(), value.get_mpz_t(), m.get_mpz_t());
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto friend operator<<(std::ostream & out, ZMod<Mod> const& x) -> std::ostream & {
|
||||||
|
return out << x.value.get_ui();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
1
zmod/src/zmod.cpp
Normal file
1
zmod/src/zmod.cpp
Normal file
|
@ -0,0 +1 @@
|
||||||
|
#include <zmod.hpp>
|
Loading…
Reference in New Issue
Block a user