tint: Misc hash / container contract improvements
Add a hash implementation to tint::Number.
Add a utils::Hasher specialization for std::variant.
Add an operator!= for Vector. Needed for std::variants.
Drop the need for explicit on Vector constructors from refs.
These all help general usage with STL and util containers.
Change-Id: I1e594edf532e78f531062c534dacaee7616cded5
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/100905
Reviewed-by: Dan Sinclair <dsinclair@chromium.org>
Commit-Queue: Ben Clayton <bclayton@google.com>
diff --git a/src/tint/number.h b/src/tint/number.h
index a36ccfb..4635051 100644
--- a/src/tint/number.h
+++ b/src/tint/number.h
@@ -496,4 +496,19 @@
} // namespace tint::number_suffixes
+namespace std {
+
+/// Custom std::hash specialization for tint::Number<T>
+template <typename T>
+class hash<tint::Number<T>> {
+ public:
+ /// @param n the Number
+ /// @return the hash value
+ inline std::size_t operator()(const tint::Number<T>& n) const {
+ return std::hash<decltype(n.value)>()(n.value);
+ }
+};
+
+} // namespace std
+
#endif // SRC_TINT_NUMBER_H_
diff --git a/src/tint/utils/hash.h b/src/tint/utils/hash.h
index ad53841..717b35f 100644
--- a/src/tint/utils/hash.h
+++ b/src/tint/utils/hash.h
@@ -20,6 +20,7 @@
#include <functional>
#include <tuple>
#include <utility>
+#include <variant>
#include <vector>
#include "src/tint/utils/vector.h"
@@ -117,6 +118,16 @@
}
};
+/// Hasher specialization for std::tuple
+template <typename... TYPES>
+struct Hasher<std::variant<TYPES...>> {
+ /// @param variant the variant to hash
+ /// @returns a hash of the tuple
+ size_t operator()(const std::variant<TYPES...>& variant) const {
+ return std::visit([](auto&& val) { return Hash(val); }, variant);
+ }
+};
+
/// @returns a hash of the variadic list of arguments.
/// The returned hash is dependent on the order of the arguments.
template <typename... ARGS>
diff --git a/src/tint/utils/vector.h b/src/tint/utils/vector.h
index b718840..f0cbf58 100644
--- a/src/tint/utils/vector.h
+++ b/src/tint/utils/vector.h
@@ -243,11 +243,11 @@
/// Move constructor from a mutable vector reference
/// @param other the vector reference to move
- explicit Vector(VectorRef<T>&& other) { MoveOrCopy(std::move(other)); }
+ Vector(VectorRef<T>&& other) { MoveOrCopy(std::move(other)); } // NOLINT(runtime/explicit)
/// Copy constructor from an immutable vector reference
/// @param other the vector reference to copy
- explicit Vector(const VectorRef<T>& other) { Copy(other.slice_); }
+ Vector(const VectorRef<T>& other) { Copy(other.slice_); } // NOLINT(runtime/explicit)
/// Destructor
~Vector() { ClearAndFree(); }
@@ -475,6 +475,12 @@
return true;
}
+ /// Inequality operator
+ /// @param other the other vector
+ /// @returns true if this vector is not the same length as `other`, or all elements are not
+ /// equal.
+ bool operator!=(const Vector& other) const { return !(*this == other); }
+
private:
/// Friend class (differing specializations of this class)
template <typename, size_t>