I was writing a zip_iterator
(for fun/academic/"oh noes Boost is evil we don't want it" reasons) and one of the use cases I envisioned is zipping two vector
s together into another container, such as a map
. This worked on Clang with libc++, but failed unexpectedly on MSVC2017 and GCC 7.2. I reduced the problem to this code:
#include <iterator>
#include <map>
#include <tuple>
int main()
{
std::map<int, double> map;
auto it = std::inserter(map, map.begin());
it = std::make_tuple(1, 1.);
}
Working demo for Clang here , broken demo's for GCC here and MSVC here .
This makes elegant use of my zip_iterator
not work:
std::copy(zip_begin(ints, doubles), zip_end(ints, doubles), std::inserter(int_double_map, int_double_map.begin()));
See here for the full code of that zip_iterator
as I have it now.
I expect this to work because a tuple is a 2-pair element and one should be constructible from the other. If I try to find a generic pair(tuple) constructor, or a tuple to pair implicit conversion, I can't seem to find one. So then the question becomes: why does it work on Clang/libc++ at all?
Note: I can't just shove an std::make_pair
in there, because, well, it's generic code.
A possible workaround would be to special-case the two-iterator case to produce a pair
instead of a tuple
. Seems ugly, but doable. I'd rather avoid that if at all possible.
and one should be constructible from the other
std::pair<T, U>
does not define any implicit constructor from std::tuple<T, U>
.
Similarly, std::tuple<T, U>
does not define any implicit conversion operator to std::pair<T, U>
.
I think Clang (libc++) is incorrect here, and that GCC and MSVC are correct.
Seems ugly, but doable
It's not too bad:
template <typename... Ts>
auto make_thing(Ts&&... xs)
{
if constexpr(sizeof...(xs) == 2))
{
return std::make_pair(std::forward<Ts>(xs)...);
}
else
{
return std::make_tuple(std::forward<Ts>(xs)...);
}
}
In C++14, you can replace if constexpr
with specialization/ enable_if
or static_if
.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.