Reputation: 125
after years of writing Java, I would like to dig deeper into C++ again.
Although I think I can handle it, I don't know if I handle it the "state of the art"-way.
Currently I try to understand how to handle std::strings passed as const pointer to as parameter to a method.
In my understanding, any string manipulations I would like to perform on the content of the pointer (the actual string) are not possible because it is const.
I have a method that should convert the given string to lower case and I did quite a big mess (I believe) in order to make the given string editable. Have a look:
class Util
{
public:
static std::string toLower(const std::string& word)
{
// in order to make a modifiable string from the const parameter
// copy into char array and then instantiate new sdt::string
int length = word.length();
char workingBuffer[length];
word.copy(workingBuffer, length, 0);
// create modifiable string
std::string str(workingBuffer, length);
std::cout << str << std::endl;
// string to lower case (include <algorithm> for this!!!!)
std::transform(str.begin(), str.end(), str.begin(), ::tolower);
std::cout << str << std::endl;
return str;
}
};
Especially the first part, where I use the char buffer, to copy the given string into a modifiable string annoys me. Are there better ways to implement this?
Regards, Maik
Upvotes: 2
Views: 1030
Reputation: 45444
As you must make a copy of the input string, you may as well take it by value (also better use a namespace than a class with static
members):
namespace util {
// modifies the input string (taken by reference), then returns a reference to
// the modified string
inline std::string&convert_to_lower(std::string&str)
{
for(auto&c : str)
c = std::tolower(static_cast<unsigned char>(c));
return str;
}
// returns a modified version of the input string, taken by value such that
// the passed string at the caller remains unaltered
inline std::string to_lower(std::string str)
{
// str is a (deep) copy of the string provided by caller
convert_to_lower(str);
// return-value optimisation ensures that no deep copy is made upon return
return str;
}
}
std::string str = "Hello";
auto str1 = util::to_lower(str);
std::cout << str << ", " << str1 << std::endl;
leaves str
un-modified: it prints
Hello, hello
See here for why I cast to unsigned char
.
Upvotes: 0
Reputation: 122585
The parameter is const
(its a reference not a pointer!) but that does not prevent you from copying it:
// create modifiable string
std::string str = word;
That being said, why did you make the parameter a const
reference in the first place? Using a const
reference is good to avoid the parameter being copyied, but if you need the copy anyhow, then simply go with a copy:
std::string toLower(std::string word) {
std::transform(word.begin(), word.end(), word.begin(), ::tolower);
// ....
Remeber that C++ is not Java and values are values not references, ie copies are real copies and modifiying word
inside the function won't have any effect on the parameter that is passed to the function.
Upvotes: 7
Reputation: 23536
you should replace all this:
// in order to make a modifiable string from the const parameter
// copy into char array and then instantiate new sdt::string
int length = word.length();
char workingBuffer[length];
word.copy(workingBuffer, length, 0);
// create modifiable string
std::string str(workingBuffer, length);
with simple this:
std::string str(word);
and it should work just fine =)
Upvotes: 2