Let rw = ranges::views
.
I'm trying to create exclusively using range-v3
an analog of the construction:
std::vector<int> v;
// range = {0, 1, 2}
auto range = rw::ints (0, 3);
for (int i : range)
for (int j : range)
v.push_back (func (i, j))
// v = {func (0, 0), func (0, 1), func (0, 2),
// func (1, 0), func (1, 1), func (1, 2),
// func (2, 0), func (2, 1), func (2, 2)}
I tried the following option:
// range = {0, 1, 2}
auto range = rw::ints (0, 3);
// range_of_ranges = {{func (0, 0), func (0, 1), func (0, 2)},
// {func (1, 0), func (1, 1), func (1, 2)},
// {func (2, 0), func (2, 1), func (2, 2)}}
auto range_of_ranges = rw::transform (range, [] (int i) {
return rw::transform (range, [i] (int j) { return func (i, j); });
});
// result = {func (0, 0), func (0, 1), func (0, 2),
// func (1, 0), func (1, 1), func (1, 2),
// func (2, 0), func (2, 1), func (2, 2)}
auto result = rw::concat (range, range, range);
for (auto x : result)
printf ("%d\n", x);
But if I replace
// result = {func (0, 0), func (0, 1), func (0, 2),
// func (1, 0), func (1, 1), func (1, 2),
// func (2, 0), func (2, 1), func (2, 2)}
auto result = rw::concat (range, range, range);
with
// result = { {{func (0, 0), func (0, 1), func (0, 2)},
// {func (1, 0), func (1, 1), func (1, 2)},
// {func (2, 0), func (2, 1), func (2, 2)}} }
auto result = rw::concat (range_of_ranges);
there will be a compiler warning:
warning: format specifies type 'int' but the argument has type 'ranges::iota_view<int, int>' [-Wformat]
printf ("%d\n", x);
Unfortunately, it doesn't work and I don't really understand how to fix it properly. I understand that the concat function should take its arguments and combine them into a range and I just created a range of length 1, but I do not know which solution would be correct. Could you give me a hint?
UPD[1] (based on Jarod42 comment: range-v3
has views::cartesian_product
) : It turned out to simplify the code to the following:
auto range = rw::ints (0, 3);
auto cart_prod = rw::cartesian_product (range, range);
auto unpack_args_and_call_func = [] (const auto &arg) {
return std::apply (func, arg);
};
auto result = rw::transform (cart_prod, unpack_args_and_call_func);
However, using the unpacking argument does not look very nice and convenient.
UPD[2] (based on Jarod42 comment: There are also views::join
for your range_of_ranges
) : Replace
// result = {func (0, 0), func (0, 1), func (0, 2),
// func (1, 0), func (1, 1), func (1, 2),
// func (2, 0), func (2, 1), func (2, 2)}
auto result = rw::concat (range, range, range);
with
// result = { {{func (0, 0), func (0, 1), func (0, 2)},
// {func (1, 0), func (1, 1), func (1, 2)},
// {func (2, 0), func (2, 1), func (2, 2)}} }
auto result = rw::join (range_of_ranges);
Thanks to Jarod42 .
// range = {0, 1, 2}
auto range = rw::ints (0, 3);
// range_of_ranges = {{func (0, 0), func (0, 1), func (0, 2)},
// {func (1, 0), func (1, 1), func (1, 2)},
// {func (2, 0), func (2, 1), func (2, 2)}}
auto range_of_ranges = rw::transform (range, [] (int i) {
return rw::transform (range, [i] (int j) { return func (i, j); });
});
// result = {func (0, 0), func (0, 1), func (0, 2),
// func (1, 0), func (1, 1), func (1, 2),
// func (2, 0), func (2, 1), func (2, 2)}
auto result = rw::join (range_of_ranges);
for (auto x : result)
printf ("%d\n", x);
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.