了解 Boost.Hana 快速入门

Understanding Boost.Hana Quick start

我正在学习 Boost.Hana's User Manual 以了解有关 C++ 中的模板元编程和函数式编程的更多信息。

至于Real world example,我还遗漏了几点,都集中在下面函数的定义上:

template<typename Any, typename Default, typename Case, typename ...Rest>
auto process(Any a, std::type_index const& t, Default default_, Case& case_, Rest ...rest) {
    using T = typename decltype(+hana::first(case_))::type;
    return typeid(T) == t ? hana::second(case_)(*boost::unsafe_any_cast<T>(&a))
                          : process(a, t, default_, rest...);
};

以下是我的疑惑和问题:

我将尝试回答有关 using 行的问题:

  • case_ 是由 hana::make_pair(hana::type_c<T>, f) 创建的 hana::pair 类型的变量(第一个参数是类型的包装器)
  • hana::first(case_) returns 对中的第一项(类型周围的 hana::type_c 包装器)
  • +hana::first(case_) 使用一元加号将值从左值转换为右值(参见 https://www.boost.org/doc/libs/1_68_0/libs/hana/doc/html/structboost_1_1hana_1_1type.html
  • decltype(+hana::first(case_)) 求值对中第一项的类型(hana::type_c 包装器)
  • decltype(+hana::first(case_))::type returns 对中第一项的实际类型(无论在 hana::type_c 中构建的类型是什么)
  • using T = typename decltype(+hana::first(case_))::type; 将该原始类型命名为 T(需要 typename 位,因为 C++ 是一种复杂的语言,有时编译器需要提示一个事物是否是一种类型或不)

你需要一些机制来提取传递给 hana::make_pair 的原始类型——如果你正在构建一些东西来解决你的特定问题,你会使其更简单,但他们需要使库如此通用它将解决每个人的问题并增加复杂性。

至于第二 return 行:

该示例的整个前提是 switch_ 被传递了一个 boost::any 并且它使用 boost::any.

的内容调用正确的 lambda

hana::second(case_) 是最初提供给 switch_ 的 lambda 之一,因此如果您使用 hana::second(case_)(a) 那么 boost::any 会传递给您的 lambda,但 lambda 中的代码不期望 boost::any 所以错误消息说 std::to_string 不接受 boost::any.

您实际上可以使用 hana::second(case_)(a),然后将 boost::any 参数转换回 lambda 中的原始类型。这实际上可以正常工作,但我认为 switch_ 应该为您做一些事情,以便 lambda 获得您期望的类型。

不幸的是 boost::any 需要如此糟糕的转换语法。