std::transform() and toupper(), no matching function
Just use ::toupper
instead of std::toupper
. That is, toupper
defined in the global namespace, instead of the one defined in std
namespace.
std::transform(s.begin(), s.end(), std::back_inserter(out), ::toupper);
Its working : http://ideone.com/XURh7
Reason why your code is not working : there is another overloaded function toupper
in the namespace std
which is causing problem when resolving the name, because compiler is unable to decide which overload you're referring to, when you simply pass std::toupper
. That is why the compiler is saying unresolved overloaded function type
in the error message, which indicates the presence of overload(s).
So to help the compiler in resolving to the correct overload, you've to cast std::toupper
as
(int (*)(int))std::toupper
That is, the following would work:
//see the last argument, how it is casted to appropriate type
std::transform(s.begin(), s.end(), std::back_inserter(out),(int (*)(int))std::toupper);
Check it out yourself: http://ideone.com/8A6iV
C++ Error: no matching function for call to 'toupper'
- You need to include the appropriate headers, in this case
<string>
and<cctype>
. - You need to specify the namespaces, in this case
std::
(use sayusing namespace std
, but that is not a good idea). it
is not a character. It is an iterator into the string. Think of it as a pointer-like object. When you want to change a character pointed to byp
, you would say*p = do_something_with(*p)
, notp = do_something_with(p)
which would change the pointer.
Thus if we write:
#include <iostream>
#include <cctype>
int main()
{
std::string s("some string");
if (s.begin() != s.end()) {
auto it = s.begin();
*it = std::toupper(*it);
}
}
then this compiles (GodBolt.org).
C++ std::transform() and toupper() ..why does this fail?
There is no space in out
. C++ algorithms do not grow their target containers automatically. You must either make the space yourself, or use a inserter adaptor.
To make space in out
, do this:
out.resize(s.length());
[edit] Another option is to create the output string with correct size with this constructor.
std::string out(s.length(), 'X');
convert a string into uppercase but getting error?
Your code is mixing C++ strings and C-style char * strings. s.c_str() may work, but can't be guaranteed in this case. convertToUpper(s.c_str()) is going to modify the array returned by c_str() and C++ gives no assurances that this will behave the way you want. The next problem will be passing the char * returned by convertToUpper into dataHolderMap.find, which is expecting a string, not a char *.
Best to keep the string a string.
Unless you have a need to preserve the input string s, take a good look at std::transform. If you need to preserve s, make a copy first and run transform on the copy.
std::transform(s.begin(), s.end(), s.begin(), ::toupper);
Will do the conversion you want and keep the string a string so that the call to dataHolderMap.find() gets the string it needs.
#include <algorithm>
...
std::string uppercase = s;
std::transform(uppercase.begin(), uppercase.end(), uppercase.begin(), ::toupper);
std::map<std::string, Code>::iterator it = dataHolderMap.find(uppercase);
Alternative is to use the Boost library in place of transform. Warning: Boost can be a pretty expensive hammer if you don't already have it installed and configured.
#include <boost/algorithm/string.hpp>
...
std::map<std::string, Code>::iterator it = dataHolderMap.find(boost::to_upper_copy(s));
Convert string to all uppercase leters with std::transform
Use ostream_iterator<char>
instead of ostream_iterator<string>
:
transform(s.begin(),s.end(),ostream_iterator<char>(cout,"\n"),std::toupper);
std::transform
transforms each character and pass it to the output iterator. That is why the type argument of the output iterator should be char
instead of std::string
.
By the way, each character will be printed on a newline. Is that what you want? If not, don't pass "\n"
.
--
Note : You may have to use ::toupper
instead of std::toupper
.
See these
- http://www.ideone.com/x6FB5 (each character on a newline)
- http://www.ideone.com/RcEKn (all characters on the same line)
Converting German Letters to Uppercase won't work
You are searching for uppercase letters and replacing them with lowercase letters.
If you want to make the letters to uppercase, you have to do the opposite.
string makeUpperCase(string c)
{
transform(c.begin(), c.end(), c.begin(), ::toupper);
while(c.find("ä") != string::npos)
{
c.replace(c.find("ä"), 2, "Ä");
}
while(c.find("å") != string::npos)
{
c.replace(c.find("å"), 2, "Å");
}
while(c.find("ö") != string::npos)
{
c.replace(c.find("ö"), 2, "Ö");
}
return c;
}
Related Topics
Windows 7 Timing Functions - How to Use Getsystemtimeadjustment Correctly
Getting Mangled Name from Demangled Name
Read Unicode Utf-8 File into Wstring
Is a Moved-From Vector Always Empty
How Do Objects Work in X86 at the Assembly Level
Change the Current Working Directory in C++
Why Is Std::Function Not Equality Comparable
Linking Fortran and C++ Binaries Using Gcc
End of File(Eof) of Standard Input Stream (Stdin)
How to Write Custom Input Stream in C++
Any Reason to Overload Global New and Delete
Why Do You Use Std::Move When You Have && in C++11
Passing a Std::Array of Unknown Size to a Function
Writing Universal Memoization Function in C++11