yai*_*chu 3 c++ option-type stdoptional
我尝试迭代std::optional:
for (auto x : optionalValue)
{
...
}
Run Code Online (Sandbox Code Playgroud)
预期如果为optionalValue空则不执行任何操作,但如果其中有值则执行一次迭代,就像它在 Haskell 中一样(可以说这很std::optional流行):
forM optionalValue
( \x ->
...
)
Run Code Online (Sandbox Code Playgroud)
为什么我不能迭代可选的?还有另一种更标准的 C++ 方法可以做到这一点吗?
std::optional没有begin()andend()对。所以你不能基于范围来超过它。相反,只需使用if条件即可。
请参阅替代方案 2,了解最接近您想要做的事情。
编辑:如果您有临时的调用结果,则不必明确检查它:
if (auto const opt = function_call()) {
do_smth(*opt);
}
Run Code Online (Sandbox Code Playgroud)
的检查static_cast<bool>(opt)是由 隐式完成的if。
替代方案1
另一种选择是不使用std::optional<T>but std::variant<std::monostate, T>。然后,您可以使用overloaded惯用法或创建自定义类型来处理单态:
template <typename F>
struct MaybeDo {
F f;
void operator()(std::monostate) const {}
template <typename T>
void operator()(T const& t) const { f(t); }
};
Run Code Online (Sandbox Code Playgroud)
这将允许您使用某些函数访问该值:
std::variant<std::monostate, int> const opt = 7;
std::visit(MaybeDo{[](int i) { std::cout << i << "\n"; }}, opt);
Run Code Online (Sandbox Code Playgroud)
替代方案2
您还可以将可选内容包装在允许您对其进行迭代的事物中。主意:
template <typename T>
struct IterateOpt {
std::optional<T> const& opt;
struct It {
std::optional<T> const* p;
It& operator++() {
p = nullptr;
return *this;
}
It operator++(int) {
return It{nullptr};
}
auto const& operator*() const { **p; }
};
auto begin() const {
if (opt) return It{&opt};
else end();
}
auto end() const {
return It{nullptr};
}
};
Run Code Online (Sandbox Code Playgroud)
这是如何执行此操作的粗略草图,可能需要一些热爱才能处理不同的情况(例如非常量可选)。
您可以使用它来“迭代”可选的:
for (auto const& v: IterateOpt{function_call()}) {
do_smth(v);
)
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
644 次 |
| 最近记录: |