Format all the code

This commit is contained in:
momo5502
2025-01-06 17:13:33 +01:00
parent 64c2a79f0f
commit bff8420ffd
100 changed files with 16439 additions and 14509 deletions

View File

@@ -5,114 +5,114 @@
namespace utils
{
template <typename T, typename S = const uint8_t>
requires(std::is_trivially_copyable_v<T> && std::is_same_v<uint8_t, std::remove_cv_t<S>>)
class safe_object_accessor
{
public:
safe_object_accessor(const std::span<S> buffer, const size_t offset)
: buffer_(buffer)
, offset_(offset)
{
}
template <typename T, typename S = const uint8_t>
requires(std::is_trivially_copyable_v<T> && std::is_same_v<uint8_t, std::remove_cv_t<S>>)
class safe_object_accessor
{
public:
safe_object_accessor(const std::span<S> buffer, const size_t offset)
: buffer_(buffer),
offset_(offset)
{
}
/*****************************************************************************
* Object is copied to make sure platform-dependent alignment requirements
* are respected
****************************************************************************/
/*****************************************************************************
* Object is copied to make sure platform-dependent alignment requirements
* are respected
****************************************************************************/
T get(const size_t element_index = 0) const
{
T value{};
memcpy(&value, get_valid_pointer(element_index), size);
return value;
}
T get(const size_t element_index = 0) const
{
T value{};
memcpy(&value, get_valid_pointer(element_index), size);
return value;
}
void set(const T value, const size_t element_index = 0) const
{
memcpy(get_valid_pointer(element_index), &value, size);
}
void set(const T value, const size_t element_index = 0) const
{
memcpy(get_valid_pointer(element_index), &value, size);
}
private:
static constexpr auto size = sizeof(T);
private:
static constexpr auto size = sizeof(T);
std::span<S> buffer_{};
size_t offset_{};
std::span<S> buffer_{};
size_t offset_{};
S* get_valid_pointer(const size_t element_index) const
{
const auto start_offset = offset_ + (size * element_index);
const auto end_offset = start_offset + size;
if (end_offset > buffer_.size())
{
throw std::runtime_error("Buffer accessor overflow");
}
S* get_valid_pointer(const size_t element_index) const
{
const auto start_offset = offset_ + (size * element_index);
const auto end_offset = start_offset + size;
if (end_offset > buffer_.size())
{
throw std::runtime_error("Buffer accessor overflow");
}
return buffer_.data() + start_offset;
}
};
return buffer_.data() + start_offset;
}
};
template <typename T>
requires(std::is_same_v<uint8_t, std::remove_cv_t<T>>)
class safe_buffer_accessor
{
public:
safe_buffer_accessor(const std::span<T> buffer)
: buffer_(buffer)
{
}
template <typename T>
requires(std::is_same_v<uint8_t, std::remove_cv_t<T>>)
class safe_buffer_accessor
{
public:
safe_buffer_accessor(const std::span<T> buffer)
: buffer_(buffer)
{
}
template <typename S>
safe_buffer_accessor(const safe_buffer_accessor<S>& obj)
: buffer_(obj.get_buffer())
{
}
template <typename S>
safe_buffer_accessor(const safe_buffer_accessor<S>& obj)
: buffer_(obj.get_buffer())
{
}
template <typename S>
safe_object_accessor<S, T> as(const size_t offset) const
{
return {this->buffer_, offset};
}
template <typename S>
safe_object_accessor<S, T> as(const size_t offset) const
{
return {this->buffer_, offset};
}
T* get_pointer_for_range(const size_t offset, const size_t size) const
{
this->validate(offset, size);
return this->buffer_.data() + offset;
}
T* get_pointer_for_range(const size_t offset, const size_t size) const
{
this->validate(offset, size);
return this->buffer_.data() + offset;
}
void validate(const size_t offset, const size_t size) const
{
const auto end = offset + size;
if (end > buffer_.size())
{
throw std::runtime_error("Buffer accessor overflow");
}
}
void validate(const size_t offset, const size_t size) const
{
const auto end = offset + size;
if (end > buffer_.size())
{
throw std::runtime_error("Buffer accessor overflow");
}
}
template <typename S = char>
std::basic_string<S> as_string(const size_t offset) const
{
safe_object_accessor<S> string_accessor{this->buffer_, offset};
std::basic_string<S> result{};
template <typename S = char>
std::basic_string<S> as_string(const size_t offset) const
{
safe_object_accessor<S> string_accessor{this->buffer_, offset};
std::basic_string<S> result{};
while (true)
{
auto value = string_accessor.get(result.size());
if (!value)
{
return result;
}
while (true)
{
auto value = string_accessor.get(result.size());
if (!value)
{
return result;
}
result.push_back(std::move(value));
}
}
result.push_back(std::move(value));
}
}
std::span<T> get_buffer() const
{
return this->buffer_;
}
std::span<T> get_buffer() const
{
return this->buffer_;
}
private:
const std::span<T> buffer_{};
};
private:
const std::span<T> buffer_{};
};
}

View File

@@ -4,54 +4,60 @@
namespace utils::concurrency
{
template <typename T, typename MutexType = std::mutex>
class container
{
public:
template <typename R = void, typename F>
R access(F&& accessor) const
{
std::lock_guard<MutexType> _{mutex_};
return accessor(object_);
}
template <typename T, typename MutexType = std::mutex>
class container
{
public:
template <typename R = void, typename F>
R access(F&& accessor) const
{
std::lock_guard<MutexType> _{mutex_};
return accessor(object_);
}
template <typename R = void, typename F>
R access(F&& accessor)
{
std::lock_guard<MutexType> _{mutex_};
return accessor(object_);
}
template <typename R = void, typename F>
R access(F&& accessor)
{
std::lock_guard<MutexType> _{mutex_};
return accessor(object_);
}
template <typename R = void, typename F>
R access_with_lock(F&& accessor) const
{
std::unique_lock<MutexType> lock{mutex_};
return accessor(object_, lock);
}
template <typename R = void, typename F>
R access_with_lock(F&& accessor) const
{
std::unique_lock<MutexType> lock{mutex_};
return accessor(object_, lock);
}
template <typename R = void, typename F>
R access_with_lock(F&& accessor)
{
std::unique_lock<MutexType> lock{mutex_};
return accessor(object_, lock);
}
template <typename R = void, typename F>
R access_with_lock(F&& accessor)
{
std::unique_lock<MutexType> lock{mutex_};
return accessor(object_, lock);
}
T& get_raw() { return object_; }
const T& get_raw() const { return object_; }
T& get_raw()
{
return object_;
}
const T& get_raw() const
{
return object_;
}
T copy() const
{
std::unique_lock<MutexType> lock{mutex_};
return object_;
}
T copy() const
{
std::unique_lock<MutexType> lock{mutex_};
return object_;
}
std::unique_lock<MutexType> acquire_lock()
{
return std::unique_lock<MutexType>{mutex_};
}
std::unique_lock<MutexType> acquire_lock()
{
return std::unique_lock<MutexType>{mutex_};
}
private:
mutable MutexType mutex_{};
T object_{};
};
private:
mutable MutexType mutex_{};
T object_{};
};
}

View File

@@ -7,19 +7,19 @@
namespace utils
{
struct string_hash
{
using is_transparent = void;
struct string_hash
{
using is_transparent = void;
size_t operator()(const std::string_view str) const
{
constexpr std::hash<std::string_view> hasher{};
return hasher(str);
}
};
size_t operator()(const std::string_view str) const
{
constexpr std::hash<std::string_view> hasher{};
return hasher(str);
}
};
template <typename T>
using unordered_string_map = std::unordered_map<std::string, T, string_hash, std::equal_to<>>;
template <typename T>
using unordered_string_map = std::unordered_map<std::string, T, string_hash, std::equal_to<>>;
using unordered_string_set = std::unordered_set<std::string, string_hash, std::equal_to<>>;
using unordered_string_set = std::unordered_set<std::string, string_hash, std::equal_to<>>;
}

View File

@@ -5,91 +5,91 @@
namespace utils
{
class file_handle
{
public:
file_handle() = default;
class file_handle
{
public:
file_handle() = default;
file_handle(FILE* file)
: file_(file)
{
}
file_handle(FILE* file)
: file_(file)
{
}
~file_handle()
{
this->release();
}
~file_handle()
{
this->release();
}
file_handle(const file_handle&) = delete;
file_handle& operator=(const file_handle&) = delete;
file_handle(const file_handle&) = delete;
file_handle& operator=(const file_handle&) = delete;
file_handle(file_handle&& obj) noexcept
: file_handle()
{
this->operator=(std::move(obj));
}
file_handle(file_handle&& obj) noexcept
: file_handle()
{
this->operator=(std::move(obj));
}
file_handle& operator=(file_handle&& obj) noexcept
{
if (this != &obj)
{
this->release();
this->file_ = obj.file_;
obj.file_ = {};
}
file_handle& operator=(file_handle&& obj) noexcept
{
if (this != &obj)
{
this->release();
this->file_ = obj.file_;
obj.file_ = {};
}
return *this;
}
return *this;
}
file_handle& operator=(FILE* file) noexcept
{
this->release();
this->file_ = file;
file_handle& operator=(FILE* file) noexcept
{
this->release();
this->file_ = file;
return *this;
}
return *this;
}
[[nodiscard]] operator bool() const
{
return this->file_;
}
[[nodiscard]] operator bool() const
{
return this->file_;
}
[[nodiscard]] operator FILE*() const
{
return this->file_;
}
[[nodiscard]] operator FILE*() const
{
return this->file_;
}
[[nodiscard]] int64_t size() const
{
const auto current_position = this->tell();
[[nodiscard]] int64_t size() const
{
const auto current_position = this->tell();
this->seek_to(0, SEEK_END);
const auto size = this->tell();
this->seek_to(current_position);
this->seek_to(0, SEEK_END);
const auto size = this->tell();
this->seek_to(current_position);
return size;
}
return size;
}
bool seek_to(const int64_t position, const int origin = SEEK_SET) const
{
return _fseeki64(this->file_, position, origin) == 0;
}
bool seek_to(const int64_t position, const int origin = SEEK_SET) const
{
return _fseeki64(this->file_, position, origin) == 0;
}
[[nodiscard]] int64_t tell() const
{
return _ftelli64(this->file_);
}
[[nodiscard]] int64_t tell() const
{
return _ftelli64(this->file_);
}
private:
FILE* file_{};
private:
FILE* file_{};
void release()
{
if (this->file_)
{
(void)fclose(this->file_);
this->file_ = {};
}
}
};
void release()
{
if (this->file_)
{
(void)fclose(this->file_);
this->file_ = {};
}
}
};
}

View File

@@ -4,52 +4,53 @@
namespace utils
{
/*
* Copied from here: https://github.com/microsoft/GSL/blob/e0880931ae5885eb988d1a8a57acf8bc2b8dacda/include/gsl/util#L57
*/
/*
* Copied from here:
* https://github.com/microsoft/GSL/blob/e0880931ae5885eb988d1a8a57acf8bc2b8dacda/include/gsl/util#L57
*/
template <class F>
class final_action
{
public:
static_assert(!std::is_reference<F>::value && !std::is_const<F>::value &&
!std::is_volatile<F>::value,
"Final_action should store its callable by value");
template <class F>
class final_action
{
public:
static_assert(!std::is_reference<F>::value && !std::is_const<F>::value && !std::is_volatile<F>::value,
"Final_action should store its callable by value");
explicit final_action(F f) noexcept : f_(std::move(f))
{
}
explicit final_action(F f) noexcept
: f_(std::move(f))
{
}
final_action(final_action&& other) noexcept
: f_(std::move(other.f_)), invoke_(std::exchange(other.invoke_, false))
{
}
final_action(final_action&& other) noexcept
: f_(std::move(other.f_)),
invoke_(std::exchange(other.invoke_, false))
{
}
final_action(const final_action&) = delete;
final_action& operator=(const final_action&) = delete;
final_action& operator=(final_action&&) = delete;
final_action(const final_action&) = delete;
final_action& operator=(const final_action&) = delete;
final_action& operator=(final_action&&) = delete;
~final_action() noexcept
{
if (invoke_) f_();
}
~final_action() noexcept
{
if (invoke_)
f_();
}
// Added by momo5502
void cancel()
{
invoke_ = false;
}
// Added by momo5502
void cancel()
{
invoke_ = false;
}
private:
F f_;
bool invoke_{true};
};
private:
F f_;
bool invoke_{true};
};
template <class F>
final_action<typename std::remove_cv<typename std::remove_reference<F>::type>::type>
finally(F&& f) noexcept
{
return final_action<typename std::remove_cv<typename std::remove_reference<F>::type>::type>(
std::forward<F>(f));
}
template <class F>
final_action<typename std::remove_cv<typename std::remove_reference<F>::type>::type> finally(F&& f) noexcept
{
return final_action<typename std::remove_cv<typename std::remove_reference<F>::type>::type>(std::forward<F>(f));
}
}

View File

@@ -4,121 +4,123 @@
namespace utils::io
{
bool remove_file(const std::filesystem::path& file)
{
std::error_code ec{};
return std::filesystem::remove(file, ec) && !ec;
}
bool remove_file(const std::filesystem::path& file)
{
std::error_code ec{};
return std::filesystem::remove(file, ec) && !ec;
}
bool move_file(const std::filesystem::path& src, const std::filesystem::path& target)
{
copy_folder(src, target);
return remove_file(src);
}
bool move_file(const std::filesystem::path& src, const std::filesystem::path& target)
{
copy_folder(src, target);
return remove_file(src);
}
bool file_exists(const std::filesystem::path& file)
{
return std::ifstream(file).good();
}
bool file_exists(const std::filesystem::path& file)
{
return std::ifstream(file).good();
}
bool write_file(const std::filesystem::path& file, const std::vector<uint8_t>& data, const bool append)
{
if (file.has_parent_path())
{
io::create_directory(file.parent_path());
}
bool write_file(const std::filesystem::path& file, const std::vector<uint8_t>& data, const bool append)
{
if (file.has_parent_path())
{
io::create_directory(file.parent_path());
}
std::ofstream stream(
file, std::ios::binary | std::ofstream::out | (append ? std::ofstream::app : std::ofstream::out));
std::ofstream stream(file, std::ios::binary | std::ofstream::out |
(append ? std::ofstream::app : std::ofstream::out));
if (stream.is_open())
{
stream.write(reinterpret_cast<const char*>(data.data()), static_cast<std::streamsize>(data.size()));
stream.close();
return true;
}
if (stream.is_open())
{
stream.write(reinterpret_cast<const char*>(data.data()), static_cast<std::streamsize>(data.size()));
stream.close();
return true;
}
return false;
}
return false;
}
std::vector<uint8_t> read_file(const std::filesystem::path& file)
{
std::vector<uint8_t> data;
read_file(file, &data);
return data;
}
std::vector<uint8_t> read_file(const std::filesystem::path& file)
{
std::vector<uint8_t> data;
read_file(file, &data);
return data;
}
bool read_file(const std::filesystem::path& file, std::vector<uint8_t>* data)
{
if (!data) return false;
data->clear();
bool read_file(const std::filesystem::path& file, std::vector<uint8_t>* data)
{
if (!data)
return false;
data->clear();
std::ifstream stream(file, std::ios::binary);
if (!stream) return false;
std::ifstream stream(file, std::ios::binary);
if (!stream)
return false;
*data = std::vector<uint8_t>{(std::istreambuf_iterator<char>(stream)), std::istreambuf_iterator<char>()};
return true;
}
*data = std::vector<uint8_t>{(std::istreambuf_iterator<char>(stream)), std::istreambuf_iterator<char>()};
return true;
}
std::size_t file_size(const std::filesystem::path& file)
{
std::ifstream stream(file, std::ios::binary);
std::size_t file_size(const std::filesystem::path& file)
{
std::ifstream stream(file, std::ios::binary);
if (stream)
{
stream.seekg(0, std::ios::end);
return static_cast<std::size_t>(stream.tellg());
}
if (stream)
{
stream.seekg(0, std::ios::end);
return static_cast<std::size_t>(stream.tellg());
}
return 0;
}
return 0;
}
bool create_directory(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::create_directories(directory, ec) && !ec;
}
bool create_directory(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::create_directories(directory, ec) && !ec;
}
bool directory_exists(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::is_directory(directory, ec) && !ec;
}
bool directory_exists(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::is_directory(directory, ec) && !ec;
}
bool directory_is_empty(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::is_empty(directory, ec) && !ec;
}
bool directory_is_empty(const std::filesystem::path& directory)
{
std::error_code ec{};
return std::filesystem::is_empty(directory, ec) && !ec;
}
void copy_folder(const std::filesystem::path& src, const std::filesystem::path& target)
{
std::error_code ec{};
std::filesystem::copy(src, target,
std::filesystem::copy_options::overwrite_existing |
std::filesystem::copy_options::recursive, ec);
}
void copy_folder(const std::filesystem::path& src, const std::filesystem::path& target)
{
std::error_code ec{};
std::filesystem::copy(
src, target, std::filesystem::copy_options::overwrite_existing | std::filesystem::copy_options::recursive,
ec);
}
std::vector<std::filesystem::path> list_files(const std::filesystem::path& directory, const bool recursive)
{
std::error_code code{};
std::vector<std::filesystem::path> files;
std::vector<std::filesystem::path> list_files(const std::filesystem::path& directory, const bool recursive)
{
std::error_code code{};
std::vector<std::filesystem::path> files;
if (recursive)
{
for (auto& file : std::filesystem::recursive_directory_iterator(directory, code))
{
files.push_back(file.path());
}
}
else
{
for (auto& file : std::filesystem::directory_iterator(directory, code))
{
files.push_back(file.path());
}
}
if (recursive)
{
for (auto& file : std::filesystem::recursive_directory_iterator(directory, code))
{
files.push_back(file.path());
}
}
else
{
for (auto& file : std::filesystem::directory_iterator(directory, code))
{
files.push_back(file.path());
}
}
return files;
}
return files;
}
}

View File

@@ -6,17 +6,17 @@
namespace utils::io
{
bool remove_file(const std::filesystem::path& file);
bool move_file(const std::filesystem::path& src, const std::filesystem::path& target);
bool file_exists(const std::filesystem::path& file);
bool write_file(const std::filesystem::path& file, const std::vector<uint8_t>& data, bool append = false);
bool read_file(const std::filesystem::path& file, std::vector<uint8_t>* data);
std::vector<uint8_t> read_file(const std::filesystem::path& file);
size_t file_size(const std::filesystem::path& file);
bool create_directory(const std::filesystem::path& directory);
bool directory_exists(const std::filesystem::path& directory);
bool directory_is_empty(const std::filesystem::path& directory);
void copy_folder(const std::filesystem::path& src, const std::filesystem::path& target);
bool remove_file(const std::filesystem::path& file);
bool move_file(const std::filesystem::path& src, const std::filesystem::path& target);
bool file_exists(const std::filesystem::path& file);
bool write_file(const std::filesystem::path& file, const std::vector<uint8_t>& data, bool append = false);
bool read_file(const std::filesystem::path& file, std::vector<uint8_t>* data);
std::vector<uint8_t> read_file(const std::filesystem::path& file);
size_t file_size(const std::filesystem::path& file);
bool create_directory(const std::filesystem::path& directory);
bool directory_exists(const std::filesystem::path& directory);
bool directory_is_empty(const std::filesystem::path& directory);
void copy_folder(const std::filesystem::path& src, const std::filesystem::path& target);
std::vector<std::filesystem::path> list_files(const std::filesystem::path& directory, bool recursive = false);
std::vector<std::filesystem::path> list_files(const std::filesystem::path& directory, bool recursive = false);
}

View File

@@ -10,80 +10,80 @@
namespace utils::nt
{
using HandleFunction = HANDLE();
using HandleFunction = HANDLE();
inline HANDLE null_handle()
{
return nullptr;
}
inline HANDLE null_handle()
{
return nullptr;
}
inline HANDLE invalid_handle()
{
return INVALID_HANDLE_VALUE;
}
inline HANDLE invalid_handle()
{
return INVALID_HANDLE_VALUE;
}
template <HandleFunction InvalidHandleFunction = null_handle>
class handle
{
public:
handle() = default;
template <HandleFunction InvalidHandleFunction = null_handle>
class handle
{
public:
handle() = default;
handle(const HANDLE h)
: handle_(h)
{
}
handle(const HANDLE h)
: handle_(h)
{
}
~handle()
{
if (*this)
{
CloseHandle(this->handle_);
this->handle_ = InvalidHandleFunction();
}
}
~handle()
{
if (*this)
{
CloseHandle(this->handle_);
this->handle_ = InvalidHandleFunction();
}
}
handle(const handle&) = delete;
handle& operator=(const handle&) = delete;
handle(const handle&) = delete;
handle& operator=(const handle&) = delete;
handle(handle&& obj) noexcept
: handle()
{
this->operator=(std::move(obj));
}
handle(handle&& obj) noexcept
: handle()
{
this->operator=(std::move(obj));
}
handle& operator=(handle&& obj) noexcept
{
if (this != &obj)
{
this->~handle();
this->handle_ = obj.handle_;
obj.handle_ = InvalidHandleFunction();
}
handle& operator=(handle&& obj) noexcept
{
if (this != &obj)
{
this->~handle();
this->handle_ = obj.handle_;
obj.handle_ = InvalidHandleFunction();
}
return *this;
}
return *this;
}
handle& operator=(HANDLE h) noexcept
{
this->~handle();
this->handle_ = h;
handle& operator=(HANDLE h) noexcept
{
this->~handle();
this->handle_ = h;
return *this;
}
return *this;
}
[[nodiscard]] operator bool() const
{
return this->handle_ != InvalidHandleFunction();
}
[[nodiscard]] operator bool() const
{
return this->handle_ != InvalidHandleFunction();
}
[[nodiscard]] operator HANDLE() const
{
return this->handle_;
}
[[nodiscard]] operator HANDLE() const
{
return this->handle_;
}
private:
HANDLE handle_{InvalidHandleFunction()};
};
private:
HANDLE handle_{InvalidHandleFunction()};
};
}
#endif

View File

@@ -6,45 +6,42 @@
namespace utils::string
{
inline char char_to_lower(const char val)
{
return static_cast<char>(std::tolower(static_cast<unsigned char>(val)));
}
inline char char_to_lower(const char val)
{
return static_cast<char>(std::tolower(static_cast<unsigned char>(val)));
}
inline char16_t char_to_lower(const char16_t val)
{
if (val >= u'A' && val <= u'Z')
{
return val + 32;
}
inline char16_t char_to_lower(const char16_t val)
{
if (val >= u'A' && val <= u'Z')
{
return val + 32;
}
return val;
}
return val;
}
inline wchar_t char_to_lower(const wchar_t val)
{
return std::towlower(val);
}
inline wchar_t char_to_lower(const wchar_t val)
{
return std::towlower(val);
}
template <class Elem, class Traits, class Alloc>
void to_lower_inplace(std::basic_string<Elem, Traits, Alloc>& str)
{
std::ranges::transform(str, str.begin(), [](const Elem e)
{
return char_to_lower(e);
});
}
template <class Elem, class Traits, class Alloc>
void to_lower_inplace(std::basic_string<Elem, Traits, Alloc>& str)
{
std::ranges::transform(str, str.begin(), [](const Elem e) { return char_to_lower(e); });
}
template <class Elem, class Traits, class Alloc>
std::basic_string<Elem, Traits, Alloc> to_lower(std::basic_string<Elem, Traits, Alloc> str)
{
to_lower_inplace(str);
return str;
}
template <class Elem, class Traits, class Alloc>
std::basic_string<Elem, Traits, Alloc> to_lower(std::basic_string<Elem, Traits, Alloc> str)
{
to_lower_inplace(str);
return str;
}
template <class Elem, class Traits, class Alloc>
std::basic_string<Elem, Traits, Alloc> to_lower_consume(std::basic_string<Elem, Traits, Alloc>& str)
{
return to_lower(std::move(str));
}
template <class Elem, class Traits, class Alloc>
std::basic_string<Elem, Traits, Alloc> to_lower_consume(std::basic_string<Elem, Traits, Alloc>& str)
{
return to_lower(std::move(str));
}
}

View File

@@ -4,23 +4,23 @@
namespace utils
{
template <typename Clock = std::chrono::high_resolution_clock>
class timer
{
public:
void update()
{
this->point_ = Clock::now();
}
template <typename Clock = std::chrono::high_resolution_clock>
class timer
{
public:
void update()
{
this->point_ = Clock::now();
}
bool has_elapsed(typename Clock::duration duration) const
{
const auto now = Clock::now();
const auto diff = now - this->point_;
return diff > duration;
}
bool has_elapsed(typename Clock::duration duration) const
{
const auto now = Clock::now();
const auto diff = now - this->point_;
return diff > duration;
}
private:
typename Clock::time_point point_{Clock::now()};
};
private:
typename Clock::time_point point_{Clock::now()};
};
}