- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我正在尝试构建一个 Filter
可以作为可组合错误处理调用的类型(即带有 << 实现 >>= 的 Maybe monad)(理想情况下)与(至少)lambda 和 std::function
一起工作在 C++17 中(不需要与旧标准兼容)。理想情况下,应该像这样工作:
// two example Filter's instantiated from lambda's
Filter g = [](const int a, const int b) -> float {
return a + b;
};
Filter f = [](const float c) -> std::optional<int> {
if c < 0 return std::nullopt;
else return c + 1;
};
// compose them - only two right now for brevity
auto h = f << g; // so that this implements f(g(...))
// and then later call them with some arguments
h(1.0, 2.0);
如果任何中间函数返回std::nullopt
, 我需要整个组合返回 std::nullopt
并为此可以处理任意数量的组合函数(可能返回也可能不返回可选值)。
我目前的实现(受 this post 启发)适用于 std::function
当组合两个简单的函数时,但当组合多个改变返回类型是否可选的函数时经常失败,因为类型推导非常脆弱。
#include <functional>
#include <optional>
#include <type_traits>
template <typename TReturn, typename... TArgs>
class Filter {
public:
/**
* The filter function that we evaluate.
*/
std::function<TReturn(TArgs...)> eval_;
/**
* Construct a filter from a std::function.
*/
Filter(std::function<TReturn(TArgs...)> f) : eval_(f) {}
/**
* Apply the filter to given arguments.
*/
auto operator()(TArgs... args) const {
return this->eval_(args...);
}
/**
* Compose this function, `f`, and `g`.
*/
template <typename TOReturn, typename... TOArgs>
auto operator<<(Filter<TOReturn, TOArgs...> other) const -> Filter<TReturn, std::optional<TOArgs>...> {
// the result of the resulting function f(g(...))
using TFReturn = std::optional<typename TReturn::value_type>;
// the type of the resulting function f(g(...))
using TFuncType = std::function<TFReturn(std::optional<TOArgs>...)>;
// construct (and return) the composed function
TFuncType f = [this, other](std::optional<TOArgs>... args) -> TFReturn {
// if we got a good value, perform the function composition
if ((args && ...)) {
// evaluate g over the input arguments
auto gresult = other(*(args)...);
// if we got a non-fail result from g, then call f
if (gresult) {
// and evaluate our own function over the result
return this->eval_(gresult);
}
} // END: if ((args && ...))
// if anything falls through, return failur
return std::nullopt;
};
return f;
} // END: operator<<
}; // END: class Filter
auto main() -> int {
// a couple of test functions
std::function<int(float, float)> f1 = [](const float a, const float b) -> int {
return a * b;
};
std::function<std::optional<int>(int)> f2 = [](const int c) -> std::optional<int> {
if (c < 0) return std::nullopt;
else return c;
};
std::function<std::optional<int>(int)> f3 = [](const int d) -> std::optional<int> {
if (d > 10) return 10;
else return d;
};
// these construct fine if I have explicitly typed std::function's above.
Filter f = f3;
Filter g = f2;
Filter h = f1;
// build the composition
auto F = g << h; // this works!
// auto F = f << g << h; // this does not work
// evaluate our composition over different arguments
auto x = F(1.0, 2.0);
auto y = F(-1.0, 2.0);
}
组合两个简单函数,f << g
, 有效但 f << g << h
当前失败并出现以下错误:
filter.cpp: In instantiation of ‘Filter<TReturn, std::optional<TOArgs>...> Filter<TReturn, TArgs>::operator<<(Filter<TOReturn, TOArgs ...>) const [with TOReturn = std::optional<int>; TOArgs = {int}; TReturn = std::optional<int>; TArgs = {int}]’:
filter.cpp:98:17: required from here
filter.cpp:55:43: error: no match for call to ‘(const std::function<std::optional<int>(int)>) (std::optional<int>&)’ 55 | return this->eval_(gresult); | ~~~~~~~~~~~^~~~~~~~~
In file included from /usr/include/c++/10/functional:59, from filter.cpp:1:
/usr/include/c++/10/bits/std_function.h:617:5: note: candidate: ‘_Res std::function<_Res(_ArgTypes ...)>::operator()(_ArgTypes ...) const [with _Res = std::optional<int>; _ArgTypes = {int}]’ 617 | function<_Res(_ArgTypes...)>:: | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/include/c++/10/bits/std_function.h:618:25: note: no known conversion for argument 1 from ‘std::optional<int>’ to ‘int’ 618 | operator()(_ArgTypes... __args) const | ~~~~~~~~~^~~~~~~~~~
/usr/include/c++/10/bits/std_function.h:601:7: error: ‘std::function<_Res(_ArgTypes ...)>::function(_Functor) [with _Functor = Filter<TReturn, TArgs>::operator<< <std::optional<int>, {int}>::<lambda(std::optional<int>)>; <template-parameter-2-2> = void; <template-parameter-2-3> = void; _Res = std::optional<int>; _ArgTypes = {std::optional<int>}]’, declared using local type ‘Filter<TReturn, TArgs>::operator<< <std::optional<int>, {int}>::<lambda(std::optional<int>)>’, is used but never defined [-fpermissive] 601 | function<_Res(_ArgTypes...)>::
如何修改类型推导以支持 std::optional<T>(...)
和 T(...)
在任意组合中发挥作用?或者是否有一种根本不同的方法来处理此解决方案?
最佳答案
不确定是否理解您的代码,但是...在我看来问题出在本节中(删除注释并稍微简化)
auto gresult = other(*(args)...);
if (gresult)
return this->eval_(gresult);
什么类型是gresult
?
我想你期望那是一个 std::optional
某种类型,因此您测试是否有效( if (gresult)
)并将其传递给以下 eval_()
.
但是结合 g()
会发生什么?和 h()
?并结合f()
?
如果我没理解错的话,h()
之前执行并返回 int
;所以gresult
是 int
.
当你检查
if (gresult)
你不检查 gresult
是有效的,但如果 gresult
是否为零。
但这有效(我的意思是...编译)并且整数值用于调用 g()
等待 int const
.
但是当 g()
的结果
auto gresult = other(*(args)...);
(即 std::optional<int>
)用于调用 f()
(等待 int
),你有那个
if (gresult)
正确检查是否gresult
是有效的,但是当您调用 f()
时
return this->eval_(gresult);
你传递给f()
一个std::optional<int>()
, 不是 int
.
不确定解决方案(不确定您到底想要什么以及 std::option
推导指南)但在我看来您应该强加 gresult
是 std::option
某种类型的
std::option gresult{ other( args.value()... ) };
所以下面检查
if ( gresult )
与 gresult
的有效性有关, 接下来你必须传递 gresult
的值到以下功能
return this->eval_( gresult.value() );
请注意,在以下代码中,
int a;
std::optional b{a};
std::optional c{b};
static_assert( std::is_same_v<decltype(b), std::optional<int>> );
static_assert( std::is_same_v<decltype(c), std::optional<int>> );
两者都是b
和 c
是std::optional<int>
我的意思是...使用推导指南 std::optional
, 如果参数是 std::optional
,结果类型相同。
我想这应该对你有用,但我不确定你到底想要什么。
关于c++ - 可组合的 monadic lambda/std::function with std::optional,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62903225/
main.cpp #include "Primes.h" #include int main(){ std::string choose; int num1, num2; w
似乎函数 qwertyInches() 应该可以工作但是当我在 main() 中调用它时它给了我 [Error] called object 'qwertyInches' is not a funct
我无法理解 C++ 语法的工作原理。 #include using namespace std; class Accumulator{ private: int value; public:
在 类中声明 函数成员时,我们可以同时执行这两种操作; Function first; Function() second; 它们之间有什么区别? 最佳答案 Function 代表任意函数: void
“colonna”怎么可能是一个简单的字符串: $('td.' + colonna).css('background-color','#ffddaa'); 可以正确突出显示有趣单元格的背景,并且: $
我正在尝试将网页中的动态参数中继到函数中,然后函数将它们传递给函数内部的调用。比如下面这个简化的代码片段,现在这样,直接传入参数是没有问题的。但是,如何在不为每个可能的 colorbox 参数设置 s
C++ 中是否有一种模式允许您返回一个函数,它返回一个函数本身。例如 std::function func = ...; do { func = func(); } while (func);
我正在将 Windows 程序集移植到 Linux。我有一些代码要移植。我实际上是 linux 中 C 的新手。我知道 C 基础知识是一样的! typedef struct sReader {
我一直在寻找一个很好的解释,所以我很清楚。示例: this.onDeleteHandler(index)}/> 对比 对比 this.nameChangedhandler(event, perso
function(){}.__proto__ === Function.prototype 和 Function.prototype === function(){}.__proto__ 得到不同的结
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function 据说 Propert
VBA 中的函数没有特殊类型。我很难理解如何在 Excel VBA 中将函数作为参数添加到函数中。 我想要完成的是这样的事情: function f(g as function, x as strin
所以我正在尝试制作一个包(我没有在下面包含我的 roxygen2 header ): 我有这个功能: date_from_text % dplyr::mutate(!!name := lubr
尝试从 std::function 派生一个类,对于初学者来说,继承构造函数。这是我的猜测: #include #include using namespace std; template cla
我正在尝试编写一个返回另一个函数的函数。我的目标是编写一个函数,它接受一个对象并返回另一个函数“search”。当我使用键调用搜索函数时,我想从第一个函数中给定的对象返回该键的值。 propertyO
我非常清楚函数式编程技术和命令式编程技术之间的区别。但是现在有一种普遍的趋势是谈论“函数式语言”,这确实让我感到困惑。 当然,像 Haskell 这样的一些语言比 C 等其他语言更欢迎函数式编程。但即
关闭。这个问题是opinion-based 。目前不接受答案。 想要改进这个问题吗?更新问题,以便 editing this post 可以用事实和引文来回答它。 . 已关闭 8 年前。 Improv
我在stackoverflow上查过很多类似的问题,比如call.call 1 , call.call 2 ,但我是新人,无法发表任何评论。我希望我能找到关于 JavaScript 解释器如何执行这些
向 Twilio 发送 SMS 时,Twilio 会向指定的 URL 发送多个请求,以通过 Webhook 提供该 SMS 传送的状态。我想让这个回调异步,所以我开发了一个 Cloud Functio
作为 IaC 的一部分,A 功能应用 ,让我们将其命名为 FuncAppX 是使用 Terraform 部署的,它有一个内置函数。 我需要使用 Terraform 在函数应用程序中访问相同函数的 Ur
我是一名优秀的程序员,十分优秀!