Reputation: 4458
I want to write a c++ function which converts a float to const char *. Here in this function, an argument is passed to specify the decimal places that output value should represent. I have come up this functions and it works nicely.
I would like to whether, there are any better ways write this function?.
static const char* getString(float value, int decimalPlaces)
{
char strValue[sizeof value];
sprintf(strValue, "%.%df", value, decimalPlaces);
return strValue;
}
Upvotes: 0
Views: 821
Reputation: 409472
There are two major problems with your function.
To begin with the size of float
is on most platform four bytes, which means your array is only four elements. Not enough for all the digits of your floating point value. Writing out of bounds will lead to undefined behavior.
The second problem is that you return a pointer to a local variable. The array strValue
will go out of scope once the function returns, and the pointer will now be a so-called stray pointer. Dereferencing it will also lead to undefined behavior.
In short, your function does not "work nicely". It doesn't really work at all.
The obvious solution is to use std::string
and std::to_string
to convert the floating point value to a string. Then when you need a C-style null-terminated string (for whatever reason) you use the strings c_str()
member function to get such a pointer.
If you need a specific number of decimals, use an std::ostringstream
and standard I/O manipulators to format the string the way you want. If your goal is to get a string to output you can of course skip this step, and use the manipulators directly when writing the output.
Upvotes: 6
Reputation: 4493
There is a problem with your function, since char strValue[]
is deleted once you leave getMString
and you return pointer to deleted data, this is UB.
I suggest not to invent anything, but use C++11 std::to_string(float)
Upvotes: 2
Reputation: 181057
When you return strValue;
you are going to return a pointer to a local variable. That means when the function ends that variable goes away and now you have a pointer to nothing. Using that pointer is undefined behavior.
You are either going to have to use new[]
to allocate the buffer and then you need to remember to delete[]
the pointer in the call site or use something like a std::string
and let the string itself handle the memory management.
Personally I would use a std::string
and a std::stringstream
like:
static std::string getMString(float value, int decimalPlaces)
{
std::stringstream stream;
stream << std::fixed << std::setprecision(decimalPlaces) << value;
return stream.str();
}
Upvotes: 2