如何获取视图类型?

How to get type of a view?

我想将视图的定义放在单独的编译单元中,但要导出视图我需要它的类型。

// .h
auto GetView(int index, int size);
// .cpp
auto GetView(int index, int size)
{
    auto view = ranges::views::ints(-2, 3)
        | ranges::views::transform([=](auto i)
            {
                return i + index;
            }
        )
        | ranges::views::enumerate
        | ranges::views::filter([=](auto i)
            {
                return i.second >= 0 && i.second < size;
            }
        )
        ;
}

我要自己回答这个问题,但也许有人可以提出一些有用的意见。

首先你可以使用 https://devblogs.microsoft.com/oldnewthing/20200528-00/

中的 whatis
template<typename... Args> void whatis();
auto GetView(int index, int size)
{
    auto view = ...
        ;
    whatis<decltype>(view);
}

但是,我无法让给定类型的 lambda 起作用

  • class `__cdecl GetView(int,int)'::`2'::<lambda_1>
  • class `__cdecl GetView(int,int)'::`2'::<lambda_2>

所以我不得不将我的 lambda 表达式包装在 std::function

std::function<int(int)>([=](auto i)
            {
                return i + index;
            })
...
std::function<bool(std::pair<int,int>)>([=](auto i)
            {
                return i.second >= 0 && i.second < size;
            })

因此,编译器会告诉类型应该是:

// .h
struct ranges::filter_view<struct ranges::zip_view<struct ranges::detail::index_view<unsigned __int64, __int64>, struct ranges::transform_view<struct ranges::iota_view<int, int>, class std::function<int __cdecl(int)> > >, class std::function<bool __cdecl(struct std::pair<int, int>)> >
        GetView(int index, int size);

或者,您可以使用 ranges::any_view

提供的类型擦除
ranges::any_view<std::pair<int,int>>
GetView2(int index, int size)
{
    return ranges::views::ints(-2, 3)
        | ranges::views::transform([=](auto i)
            {
                return i + index;
            }
        )
        | ranges::views::enumerate
        | ranges::views::filter([=](auto i)
            {
                return i.second >= 0 && i.second < size;
            }
        )
        ;
}