#is this not the way `std::unordered_map` was intended to be used?

26 messages · Page 1 of 1 (latest)

deep pike
#
#include <unordered_map>
#include <string>
#include <string_view>
#include <memory>

struct Foo
{
    int value;
    float data;
};

struct TransparentHash
{
    using is_transparent = void; // lol, ok?
    size_t operator()(std::string_view sv) const noexcept
    {
        return std::hash<std::string_view>{}(sv);
    }
};

struct TransparentEqual // written by ai btw
{
    using is_transparent = void;
    bool operator()(std::string_view a, std::string_view b) const noexcept
    {
        return a == b;
    }
};

int main()
{
    std::unordered_map<std::string, std::unique_ptr<Foo>, TransparentHash, TransparentEqual> map;

    map.emplace("hello", std::make_unique<Foo>(42, 3.14f));
    std::string key = "hello";
    std::string_view sv = key;
    auto it = map.find(sv);
}

So apparently, this is how you pass a std::string_view as the key to a map?
So judging by the amount of nonsense to do it, this can't be useful right? Like I shouldn't bother to key the container with a std::string_view and instead just use a std::string right?
Because I have to believe that if this was a sane thing to do, then the STL would allow passing the std::string_view without this other stuff?

I mean I did this just because I thought that std::string_view is generally preferred over std::string where its possible to do so. So why might it not be in this case?

formal belfryBOT
#

When your question is answered use !solved or the button below to mark the question as resolved.

Remember to ask specific questions, provide necessary details, and reduce your question to its simplest form. For tips on how to ask a good question use !howto ask.

snow robin
#

note that you only need to do it because people didn't really think of transparent comparisons when designing the container originally, and it may necessarily be correct

blissful pilot
#

std::string_view is just useful if you trully need zero copy lookups

deep pike
#

Okay then, well thank you for confirming @snow robin , I mean i am now depressed but I appreciate the feedback

snow robin
#

you can also make an alias template so you don't need to specify all of this each time you make a map

#
template <typename T>
using TransparentStringMap = std::unordered_map<
  std::string,
  T,
  TransparentHash,
  TransparentEqual
>;
polar garden
#

I wonder why there's no stock transparent hasher, std::hash<void>

blissful pilot
#

cuz std::hash is type-specific... i think there is no generic “any type” hash in the standard

snow robin
#

propose it I guess

#

the answer in these cases is often "cause no one made a proposal yet"

blissful pilot
deep pike
#

would it be less work to a) write a paper/prposal. or b) write it into your library and move on

#

like how would I write such a std::hash<void> and then use it in this case?

blissful pilot
#

i think b) Write it into your library and move on, faster, no bureaucracy

deep pike
#

is that what the ai gave me is a std::hash<void>

#

you're talking to a brick wall that ocasionally drools btw

blissful pilot
polar garden
blissful pilot
#

say something like this

struct AnyHash {
    using is_transparent = void;

    size_t operator()(std::string_view sv) const noexcept {
        return std::hash<std::string_view>{}(sv);
    }
    size_t operator()(const std::string& s) const noexcept {
        return std::hash<std::string>{}(s);
    }
    // add more overloads as needed
};
#

then pass that to the map's hasher

#

i would say this is the closest thing to a hash<void> in practice

deep pike
#

oh boy, got it. not actually, but my brain has closed like your lungs do when you chug ammonia

formal belfryBOT
#

@deep pike Has your question been resolved? If so, type !solved :)

deep pike
#

!solved