如何定义“一元谓词"?用于C ++中的copy_if等? [英] How do I define a "unary predicate" for copy_if, etc in C++?
问题描述
I'm trying to use std::copy_if() and I figured out somewhat how the syntax works from http://www.cplusplus.com/reference/algorithm/copy_if/ :
auto it = std::copy_if (foo.begin(), foo.end(), bar.begin(), [](int i){return !(i<0);} );
最后一个参数是我很困惑的那个.括号是用来干什么的?我可以使用在其他地方编写的函数作为参数,这将如何工作?如果我指定要传递给该函数的变量,是否可以将另一个参数传递给该函数?
The last argument is the one that I am confused about. What are the brackets for? Can I use a function I wrote somewhere else as an argument and how would that work? Can I pass another argument to the function if I specify which variable to pass to it?
我想我的总体问题是,我在哪里可以找到这些语法.使用此示例,我可以声明一些非常简单的内容,但是我希望能够做更多的事情.我已经找到了一些地方来解释一元谓词应该做什么和不应该做什么,但是实际上却没有解释如何声明一个一元谓词以及这意味着什么.我对c ++中的算法还是有些陌生,希望学习如何更有效地使用它们.
I guess my overall question is where I could find the syntax for these things. Using this example, I can declare some really simple things, but I'd like to be able to do more with it. I've found a few places that explain what a unary predicate should do and not do, but not actually how to declare one and what that would mean. I'm still somewhat new to the algorithms in c++ and hope to learn how to use them more effectively.
推荐答案
您可以将行为类似于函数的任何内容作为谓词传递给 copy_if
.您可以使用一些常用的东西:
You can pass anything that behaves like a function as the predicate to copy_if
. There are a few common things you can use:
1)功能
函数的作用确实类似于函数,因此可以将它们作为谓词传递给 copy_if
:
Functions indeed act like functions, so they can be passed as a predicate to copy_if
:
bool is_less_than_zero(int i) { return i < 0; }
int main() {
std::vector<int> a = {1, 2, -2, -1};
std::vector<int> b;
std::copy_if(a.begin(), a.end(), std::back_inserter(b), is_less_than_zero);
// now b will contain the elements {-2, -1}
}
2)具有重载的 operator()
对象可以重载 operator()
,以便它们像函数一样起作用.这些通常称为功能对象"或功能部件".这可以让您存储状态,这是原始功能无法实现的:
Objects can overload operator()
so that they act like functions. These are often called "function objects" or "functors". This lets you store state, which can't be achieved with raw functions:
struct IsLessThan {
IsLessThan(int i) : i_{i} {}
bool operator()(int i) { return i < i_; }
int i_;
};
int main() {
std::vector<int> a = {1, 2, -2, -1};
std::vector<int> b;
std::copy_if(a.begin(), a.end(), std::back_inserter(b), IsLessThan(0));
// now b will contain the elements {-2, -1}
}
3) Lambdas
Lambda在概念上是匿名函数.实际上,它们只是带有 operator()
重载的对象的语法糖,但这使它们成为创建少量代码的简单谓词的有用工具:
Lambdas are conceptually anonymous functions. In reality, they're just syntactic sugar for objects with an overloaded operator()
, but that makes them a useful tool for creating simple predicates with little code:
int main() {
std::vector<int> a = {1, 2, -2, -1};
std::vector<int> b;
std::copy_if(a.begin(), a.end(), std::back_inserter(b),
[](int i){ return i < 0; });
// now b will contain the elements {-2, -1}
}
由于lambda实际上是带有重载的 operator()
的对象,因此它们还可以包含状态,该状态通过lambda的捕获列表给出:
Since lambdas are really objects with an overloaded operator()
they can also contain state, which is given via the lambda's capture list:
int main() {
std::vector<int> a = {1, 2, -2, -1};
std::vector<int> b;
int number_to_compare_to = 0;
std::copy_if(a.begin(), a.end(), std::back_inserter(b),
[number_to_compare_to](int i){ return i < number_to_compare_to; });
// now b will contain the elements {-2, -1}
}
标准库中有一些功能可以轻松创建包含状态的函数对象,并使用它为函数提供一些参数(即
There are some facilities in the standard library to easily create function objects that contain state and use it to supply some of the parameters to a function (namely std::bind
), but most of the places they were useful it's now easier to use a lambda instead. That is, the following code creates two objects that both act exactly the same:
bool first_less_than_second(int i, int j) { return i < j; }
int main() {
auto bind_less_than_zero = std::bind(first_less_than_second, std::placeholders::_1, 0);
auto lambda_less_than_zero = [](int i){ return first_less_than_second(i, 0); };
}
通常,您应该更喜欢lambda版本,但有时仍会看到 std :: bind
(或其c ++ 11之前的增强版本 boost :: bind
>)受雇.
In general you should prefer the lambda version, but you will still sometimes see std::bind
(or its pre-c++11 boost counterpart boost::bind
) employed.
这篇关于如何定义“一元谓词"?用于C ++中的copy_if等?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!