-
December 18th, 2009, 01:11 PM
#1
no matching function transform?
Hi all,
I followed the following post: http://www.codeguru.com/forum/showthread.php?t=472216 and try to test strlwr function. The test code is
Code:
#include <algorithm>
#include <string>
#include <iostream>
using namespace std;
int main (int argc, char * const argv[]){
string str = "Hello";
transform(str.begin(), str.end(), str.begin(), tolower);
cout << str << endl;
return 0;
}
but it seems that either my compiler does not have "transform" or I am missing something there, because when I compiled it, I got error
Code:
$ g++ -g -Wall strToLower.cpp -o strToLower
strToLower.cpp: In function ‘int main(int, char* const*)’:
strToLower.cpp:9: error: no matching function for call to ‘transform(__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, <unknown type>)’
Anybody helps please!
Thanks,
D.
-
December 18th, 2009, 01:13 PM
#2
Re: no matching function transform?
You didn't include <cctype>. That is where the tolower() declaration is located.
Regards,
Paul McKenzie
-
December 18th, 2009, 01:21 PM
#3
Re: no matching function transform?
Originally Posted by Paul McKenzie
You didn't include <cctype>. That is where the tolower() declaration is located.
Regards,
Paul McKenzie
Thanks Paul. I added that and I still have error
Code:
$ cat strToLower.c
#include <algorithm>
#include <string>
#include <iostream>
#include <cctype>
using namespace std;
int main (int argc, char * const argv[]){
string str = "Hello";
transform(str.begin(),str.end(),str.begin(),tolower);
cout << str << endl;
return 0;
}
$ g++ -g -Wall strToLower.c -o strToLower
strToLower.c: In function ‘int main(int, char* const*)’:
strToLower.c:10: error: no matching function for call to ‘transform(__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, <unknown type>)’
-
December 18th, 2009, 01:24 PM
#4
Re: no matching function transform?
Originally Posted by dukevn
Thanks Paul. I added that and I still have error
The program compiles correctly using Comeau.
If you changed the extension of the source file to .cpp instead of .c, what happens? What version of g++ are you using?
Regards,
Paul McKenzie
-
December 18th, 2009, 01:31 PM
#5
Re: no matching function transform?
Originally Posted by Paul McKenzie
The program compiles correctly using Comeau.
If you changed the extension of the source file to .cpp instead of .c, what happens? What version of g++ are you using?
Thanks Paul for your prompt reply. Here is the output:
Code:
$ mv strToLower.c strToLower.cpp
$ g++ -g -Wall strToLower.cpp -o strToLower
strToLower.cpp: In function ‘int main(int, char* const*)’:
strToLower.cpp:10: error: no matching function for call to ‘transform(__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, <unknown type>)’
$ g++ --version
i686-apple-darwin9-g++-4.0.1 (GCC) 4.0.1 (Apple Inc. build 5490)
Copyright (C) 2005 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
I just also tried on my remote Red Hat server, and I got error as well:
Code:
$ g++ -g -Wall strToLower.cpp -o strToLower
strToLower.cpp: In function 'int main(int, char* const*)':
strToLower.cpp:10: error: no matching function for call to 'transform(__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, <unresolved overloaded function type>)'
$ g++ --version
g++ (GCC) 4.1.2 20080704 (Red Hat 4.1.2-46)
Copyright (C) 2006 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
-
December 18th, 2009, 01:45 PM
#6
Re: no matching function transform?
It looks like you have a bad install, your #include path is not correct, or the compiler just doesn't have that function (which is hard to believe).
If you opened the <algorithm> file, do you see a transform function there? If you do, can you post the declaration of it (it will be a template function, so all we want is the declaration, not the entire body of the function).
Regards,
Paul McKenzie
-
December 18th, 2009, 01:48 PM
#7
Re: no matching function transform?
Well, the problem is that the version of std::tolower inherited from the C standard library is a non-template function, but there are other versions of std::tolower that are function templates, and it is possible for them to be included depending on the standard library implementation. You actually want to use the non-template function, but there is ambiguity when just tolower is provided as the predicate.
One workaround is to qualify the name since the non-template function may be available in the global namespace:
Code:
transform(str.begin(), str.end(), str.begin(), ::tolower);
But it may be better to define a wrapper for tolower that actually takes a char argument and returns a char (the version inherited from C takes an int argument and returns an int).
-
December 18th, 2009, 01:52 PM
#8
Re: no matching function transform?
Originally Posted by laserlight
Well, the problem is that the version of std::tolower inherited from the C standard library is a non-template function, but there are other versions of std::tolower that are function templates, and it is possible for them to be included depending on the standard library implementation.
OK, that sounds right -- I now see the
<unknown type>
error for the last argument in transform.
Regards,
Paul McKenzie
-
December 18th, 2009, 01:57 PM
#9
Re: no matching function transform?
Originally Posted by laserlight
Code:
transform(str.begin(), str.end(), str.begin(), ::tolower);
Adding "::" solved the problem. Thank you very much for your help, Paul and laserlight.
-
December 18th, 2009, 02:12 PM
#10
Re: no matching function transform?
Originally Posted by dukevn
Adding "::" solved the problem. Thank you very much for your help, Paul and laserlight.
Sorry Paul, would you mind trying the code with "::" added? The reason I ask is because if that does not work with your compiler (Corneau), then I really doubt the portability of C++ code!
Thanks.
-
December 18th, 2009, 02:24 PM
#11
Re: no matching function transform?
Originally Posted by dukevn
Sorry Paul, would you mind trying the code with "::" added? The reason I ask is because if that does not work with your compiler (Corneau), then I really doubt the portability of C++ code!
You can test with the online Comeau compiler.
However, as I implied, there is no guarantee that the non-template version of tolower will be available in the global namespace (unless you #include <ctype.h> instead). A really portable solution is to write a wrapper, e.g.,
Code:
inline char charToLower(char c)
{
return std::tolower(c);
}
// ...
transform(str.begin(), str.end(), str.begin(), charToLower);
-
December 18th, 2009, 02:50 PM
#12
Re: no matching function transform?
Originally Posted by laserlight
Thanks for the link. I tried both with and without "::" and they both worked.
Originally Posted by laserlight
However, as I implied, there is no guarantee that the non-template version of tolower will be available in the global namespace (unless you #include <ctype.h> instead). A really portable solution is to write a wrapper, e.g.,
Code:
inline char charToLower(char c)
{
return std::tolower(c);
}
// ...
transform(str.begin(), str.end(), str.begin(), charToLower);
Yeah, this one is much better. By the way, I tried also with and without "inline" and they both worked. Do I really need that "inline"?
Thanks,
D.
-
December 18th, 2009, 02:53 PM
#13
Re: no matching function transform?
Originally Posted by dukevn
Thanks for the link. I tried both with and without "::" and they both worked.
Yeah, this one is much better. By the way, I tried also with and without "inline" and they both worked. Do I really need that "inline"?
Not really. It's used as a request to the compiler to inline the code, but the actual inlining doesn't have to be granted.
Regards,
Paul McKenzie
-
December 18th, 2009, 04:08 PM
#14
Re: no matching function transform?
Originally Posted by Paul McKenzie
Not really. It's used as a request to the compiler to inline the code, but the actual inlining doesn't have to be granted.
Regards,
Paul McKenzie
Thanks Paul.
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|