microfmt
Zero-allocation C++ formatting for constrained environments
Loading...
Searching...
No Matches
hash.hpp
Go to the documentation of this file.
1// SPDX-FileCopyrightText: 2026 Jarosław Pelczar <jarek@jpelczar.com>
2//
3// SPDX-License-Identifier: BSD-2-Clause
4
5#pragma once
6
9#include "../microfmt.hpp"
10#include <cstddef>
11#include <functional>
12#include <type_traits>
13
14namespace microfmt {
15
16namespace detail {
17
22template <typename T, typename = void> struct is_hashable : std::false_type {};
23
29template <typename T>
30struct is_hashable<T, std::void_t<decltype(std::hash<T>{}(std::declval<const T &>()))>> : std::true_type {};
31
36template <typename T> inline constexpr bool is_hashable_v = is_hashable<T>::value;
37
38} // namespace detail
39
40// ============================================================================
41// Non-Owning Hash View
42// ============================================================================
43
50template <typename T> class RELOCO_POINTER hash_view {
51public:
56 constexpr explicit hash_view(const T &val RELOCO_LIFETIMEBOUND) noexcept : val_(val) {}
57
58 constexpr explicit hash_view(const T &&) = delete;
59
64 [[nodiscard]] std::size_t compute_hash() const noexcept { return std::hash<T>{}(*val_); }
65
66private:
68 value_ref<const T> val_;
69};
70
71// ============================================================================
72// Factory Function: microfmt::as_hash(...)
73// ============================================================================
74
81template <typename T, std::enable_if_t<detail::is_hashable_v<T>, int> = 0>
82[[nodiscard]] constexpr auto as_hash(const T &val RELOCO_LIFETIMEBOUND) noexcept {
83 return hash_view<T>{val};
84}
85
86template <typename T, std::enable_if_t<
87 !std::is_lvalue_reference_v<T> && detail::is_hashable_v<std::remove_reference_t<T>>, int> = 0>
88[[nodiscard]] constexpr auto as_hash(T &&) noexcept = delete;
89
90// ============================================================================
91// Formatter for hash_view
92// ============================================================================
93
102template <typename T> struct formatter<hash_view<T>> {
107
112 constexpr void parse(format_parse_context &ctx) noexcept { int_fmt_.parse(ctx); }
113
119 void format(const hash_view<T> &view, const sink &out) const noexcept { int_fmt_.format(view.compute_hash(), out); }
120};
121
122} // namespace microfmt
Definition microfmt.hpp:881
Non-owning view that defers a value's hash computation to formatting time.
Definition hash.hpp:50
constexpr hash_view(const T &val RELOCO_LIFETIMEBOUND) noexcept
Constructs a hash view referencing an existing value.
Definition hash.hpp:56
std::size_t compute_hash() const noexcept
Computes the hash of the referenced value.
Definition hash.hpp:64
constexpr hash_view(const T &&)=delete
constexpr bool is_hashable_v
Convenience variable template for is_hashable.
Definition hash.hpp:36
Definition assert.hpp:19
reloco::sink sink
Type-erased, zero-allocation output sink.
Definition microfmt.hpp:46
constexpr auto as_hash(const T &val RELOCO_LIFETIMEBOUND) noexcept
Wraps a value in an hash_view for hashed formatting.
Definition hash.hpp:82
SFINAE trait detecting types invocable through std::hash<T>.
Definition hash.hpp:22
constexpr void parse(format_parse_context &ctx) noexcept
Parses the specifier for the wrapped integer formatter.
Definition hash.hpp:112
void format(const hash_view< T > &view, const sink &out) const noexcept
Computes and renders the hash value.
Definition hash.hpp:119
Definition microfmt.hpp:985