The following code tries to define a self-similar datastructure JSON using the std containers std::vector and std::unordered_map but does not compile. It all seems to come down to std::unordered_map's hashtable deleting its destructor because it is inaccessible/private in the base class. I can't really put my fingers on why this would happen. Following my previous question any cyclic dependency regarding allocators should have been resolved and the cyclic dependencies of vectors and unordered_map's value types should be supported as of 2022.
#include <variant>
#include <unordered_map>
#include <vector>
#include <string>
#include <string_view>
#include <concepts>
#include <memory> // allocator
#include <memory_resource>
#include <cstddef> // std::size_t
template <typename StringType = std::string, typename Allocator = std::allocator<void>>
class JSON;
template <typename StringType, typename Allocator>
class JSON: public std::variant<std::monostate,
std::unordered_map<StringType, JSON<StringType, Allocator>, std::hash<JSON<StringType, Allocator>>, std::equal_to<StringType>,
typename std::allocator_traits<Allocator>::template rebind_alloc<std::pair<const StringType, JSON<StringType, Allocator>>>
>,
std::vector<JSON<StringType, Allocator>,
typename std::allocator_traits<Allocator>::template rebind_alloc<JSON<StringType, Allocator>>
>,
bool,
double,
StringType>
{
public:
using JSON::variant::variant;
};
int main() {
JSON json;
}
clang trunk says:
/opt/compiler-explorer/gcc-snapshot/lib/gcc/x86_64-linux-gnu/13.0.1/../../../../include/c++/13.0.1/bits/functional_hash.h:102:19: note: destructor of 'hash<JSON<>>' is implicitly deleted because base class '__hash_enum<JSON<basic_string<char, char_traits<char>, allocator<char>>, allocator<void>>>' has an inaccessible destructor
struct hash : __hash_enum<_Tp>
gcc trunk says:
/opt/compiler-explorer/gcc-trunk-20230415/include/c++/13.0.1/bits/functional_hash.h:84:7: note: declared private here
84 | ~__hash_enum();
|
Why would it suddenly be declared private?
To find such errors it is best to simplify the code as long as the error still occurs. In this reduced version the problem then becomes recognizable:
I think what you wanted to do is
std::hash<StringType>instead ofstd::hash<JSON<StringType, Allocator>>since the hash map needs a unique key and not a unique value.