I was looking for a way to uppercase a standard string. The answer that I found included the following code:
int main()
{
// explicit cast needed to resolve ambiguity
std::transform(myString.begin(), myString.end(), myString.begin(),
(int(*)(int)) std::toupper)
}
Can someone explain the casting expression “(int(*) (int))”? All of the other casting examples and descriptions that I’ve found only use simple type casting expressions.
As others already mentioned,
int (*)(int)is the type pointer to a function which takes and returnsint. However what is missing here is what this cast expression does: Unlike other cast expressions it does not really cast (i.e. it does not convert a value into a different type), but it selects from the overloaded set of functions namedstd::toupperthe one which has the signatureint(int).Note, however, that this method is somewhat fragile: If for some reason there’s no matching function (for example because the corresponding header was not included) but only one non-matching function (so no ambiguity arises), then this cast expression will indeed turn into a cast, more exactly a
reinterpret_cast, with undesired effects. To make sure that no unintended cast happens, the C++ style cast syntax should be used instead of the C style cast syntax:static_cast<int(*)(int)>(std::toupper)(actually, in the case ofstd::toupperthis case cannot occur because the only alternative function is templated and therefore ambiguous, however it could happen with other overloaded functions).Coincidentally, the new-style cast syntak is more readable in that case, too.
Another possibility, which works without any cast expression, is the following:
Note that the reason why the context cannot provide the necessary information is that
std::transformis templated on the last argument, therefore the compiler cannot determine the correct function to choose.