-5

Is it possible to sort vector<any> by using std::sort or somehow else?

I was trying to do smth like this

  vector<any> va{ 55ll, 'a', -1};
   
    sort(va.begin(), va.end(), [](const any& lhs, const any& rhs) { return any_cast<decltype(lhs.type())>(lhs) > any_cast<decltype(lhs.type()>(rhs) });
  • how do you want it to be sorted? – 463035818_is_not_an_ai Mar 31 '22 at 12:24
  • 3
    What does it means to compare `"foo"` with `42`? Which should be considered less? – NathanOliver Mar 31 '22 at 12:24
  • 2
    What does "I was trying to do smth like this" mean? If you tried it, what happened? If you didn't, why are you posting it? – Scott Hunter Mar 31 '22 at 12:25
  • @NathanOliver String representations of objects of different types can be sorted lexicographically (also known as _somehow_ sort order). – Maxim Egorushkin Mar 31 '22 at 12:29
  • 1
    The fundamental problem with your approach is that `lhs.type()` is a runtime function, and `decltype` is a compile-time function. C++ does not work this way, on a fundamental level. – Sam Varshavchik Mar 31 '22 at 12:30
  • Your use of `any_cast` indicates you expect, at some point, to be able to cast the `any` back to whatever type is stored automatically. It is not possible to do this with `std::any`, you eventually need to explicitly provide the type the `any` stores to the cast. This type cannot be deduced from the `std::any`. A stand alone `std::any` is basically always useless. – François Andrieux Mar 31 '22 at 13:03

1 Answers1

2

Is it possible to sort vector by using std::sort or somehow else?

It is possible. You can do it the same way as sorting anything else: By defining a function to compare two std::any with strict total order.

any_cast<decltype(lhs.type())>(lhs)

This won't work. std::any::type returns std::type_info, and unless you store an object of type std::type_info in std::any, the std::any_cast will fail.


There are many ways to order objects of heterogeneous types.

A relatively simple way is to primarily order by the type of the object. A caveat here is that the order of types is not portable across systems:

bool
any_less_type(const std::any& l, const std::any& r)
{
    auto& lt = l.type();
    auto& rt = r.type();
    return std::type_index(lt) < std::type_index(rt);
}

Then, objects of same type that are orderable may be further ordered, but that feature may have to be limited to a small set of types as if you were using std::variant.

eerorika
  • 232,697
  • 12
  • 197
  • 326