std::for_each is not compiling with boost::algorithm::to_lowe
Hello,
Do you guys know why this does not compile?
<code>
std::for_each(v.begin(), v.end(), &boost::algorithm::to_lower<string>);
</code>
v is a vector of strings that I want to convert to lowercase.
However, if I have another function
Code:
static void toLowerCase(string &s)
{
boost::algorithm::to_lower<string>(s);
}
and do like the following it works..
Code:
std::for_each(v.begin(), v.end(), toLowerCase);
compiler is g++
Thanks in advance
-Prashant
Re: std::for_each is not compiling with boost::algorithm::to_lowe
Quote:
Originally Posted by
code_carnage
Hello,
Do you guys know why this does not compile?
<code>
std::for_each(v.begin(), v.end(), &boost::algorithm::to_lower<string>);
</code>
v is a vector of strings that I want to convert to lowercase.
However, if I have another function
Code:
static void toLowerCase(string &s)
{
boost::algorithm::to_lower<string>(s);
}
and do like the following it works..
Code:
std::for_each(v.begin(), v.end(), toLowerCase);
compiler is g++
Thanks in advance
-Prashant
to_lower takes a second default std::locale argument. The problem is that you are passing a function pointer as an argument, which strips the default parameters (default parameters are determined at compile time, and function pointers are compile-time objects). Hence the "too few arguments" error.
For the algorithm to work, you'd need to wrap to_lower in a "function object". Theory would instruct you to try to use std::bind/std::function. However, I feel that the resulting code is so obscure/convoluted, you are better off doing it by hand
I'd love to see someone show me how it's done: I failed :(
In the mean time, you can either use your toLowerCase function, or write a function object:
Code:
#include <string>
#include <algorithm>
#include <boost/algorithm/string/case_conv.hpp>
#include <locale>
template<typename T>
struct to_lower_functor
{
void operator()(T& i, const std::locale& Loc = std::locale()) const
{
return boost::algorithm::to_lower<T>(i, Loc);
}
};
int main()
{
std::vector<std::string> v;
std::for_each(v.begin(), v.end(), to_lower_functor<std::string>());
}
Re: std::for_each is not compiling with boost::algorithm::to_lowe
Quote:
Originally Posted by monarch_dodra
Theory would instruct you to try to use std::bind/std::function. However, I feel that the resulting code is so obscure/convoluted, you are better off doing it by hand
I'd love to see someone show me how it's done: I failed :(
Code:
#include <functional>
#include <algorithm>
#include <vector>
#include <string>
#include <locale>
#include <boost/algorithm/string/case_conv.hpp>
using namespace std;
using namespace placeholders;
int main()
{
vector< string > Array;
for_each( Array.begin(), Array.end(), bind( &boost::algorithm::to_lower< string >, _1, locale() ) );
return 0;
}
I don't have boost to make sure that is right, but I am pretty confident.
Re: std::for_each is not compiling with boost::algorithm::to_lowe
Quote:
Originally Posted by
Joeman
Code:
#include <functional>
#include <algorithm>
#include <vector>
#include <string>
#include <locale>
#include <boost/algorithm/string/case_conv.hpp>
using namespace std;
using namespace placeholders;
int main()
{
vector< string > Array;
for_each( Array.begin(), Array.end(), bind( &boost::algorithm::to_lower< string >, _1, locale() ) );
return 0;
}
I don't have boost to make sure that is right, but I am pretty confident.
>:(
That's why it wasn't working for me: I was using _2... I keep forgetting the the index of "first" is 0, and the index of "second" is 1. The worst part is I had tried that exact piece of code...
Stupid std::pair and "bind1st"/"bind2nd" teaching me wrong.
--------
There is one thing that bothers me though (in both versions): Explicit re-statement of a default parameter. Anybody know of a way to keep the second parameter, without hand-copying the default constructor?