I am enabling a large code base to alternate between single and double floating point precision via a single typedef. At present, my code is double-oriented:
double foo(double input)
{
return 1.0/input;
}
A naive switch to programmer-specified precision looks like this:
#ifdef _USE_DOUBLES
typedef double fpType;
#else
typedef float fpType;
#endif
fpType foo(fpType input)
{
return 1.0/input;
}
Obviously, the "1.0" causes a compiler warning. My best solution so far is to treat every constant thus:
fpType foo(fpType input)
{
return fpType(1.0)/input;
}
Is there any possibility that the explicit POD constructor invocation will actually be performed at runtime, thus charging me a speed penalty just for solving compiler warnings? I suspect not, since a compile time rewrite from "fType(CONSTANT)" to "CONSTANTf" seems trivial. But I want to make absolutely sure. I use VC, but I want to know about C++ compilers in general.
Also, is there a more elegant solution than mine? The fpType() invocations get ugly when lots of constants feature in one expression:
fpType someVal = fpType(1.0)/(someOtherVal+fpType(0.5))*(someVal
/fpType(7.66))*fpType(43.33);
I expect there are compiler-specific approaches to this problem, but I seek a compiler-agnostic one, if it exists. Naturally, I would look to warning suppression only as a last resort, perhaps not at all.
[EDIT]
I wrote this question misunderstanding "direct initialization", which is explained at Constructor Initialization of primitive data types in CPP.
You may try C++11 user defined literals:
#include <iostream>
#ifdef USE_DOUBLES
constexpr double operator"" _f (double value)
{
return value;
}
#else
constexpr float operator"" _f (double value)
{
return value;
}
#endif /*USE_DOUBLE*/
using namespace std;
int main()
{
cout << 1.2_f << endl;
}
For the literal constants, you could use float type. The conversion to double will happen without any compiler warnings.
fpType foo(fpType input)
{
return 1.0f/input;
}
Related
So my understanding is that this: 1e3 Equates to 1000.0.
My question is, is there a similar shorthand for integers? I realize that I can do: static_cast<int>(1e3). Is there anything available to me outside of this?
No, there is no syntax for scientific notation integer literal in C++.
You could shorten the conversion with a user defined literal:
constexpr int operator "" _i(long double d) noexcept {
return d;
}
int main() {
auto big = 1e3_i; // is int
}
However, this does (at least on GCC that I tested) prevent the compiler from noticing overflow in the initialization so in those cases where possible, prefer the more conventional:
int big = 1e30; // compiler should yell at you
I am getting some -Wnarrowing conversion errors when doubles are narrowed to floats. How can I do this in a well defined way? Preferably with an option in a template I can toggle to switch behavior from throwing exceptions, to clamping to the nearest value, or to simple truncation. I was looking at the gsl::narrow cast, but it seems that it just performs a static cast under the hood and a comparison follow up: Understanding gsl::narrow implementation. I would like something that is more robust, as according to What are all the common undefined behaviours that a C++ programmer should know about? static_cast<> is UB if the value is unpresentable in the target type. I also really liked this implementation, but it also relies on a static_cast<>: Can a static_cast<float> from double, assigned to double be optimized away? I do not want to use boost for this. Are there any other options? It's best if this works in c++03, but c++0x(experimental c++11) is also acceptable... or 11 if really needed...
Because someone asked, here's a simple toy example:
#include <iostream>
float doubleToFloat(double num) {
return static_cast<float>(num);
}
int main( int, char**){
double source = 1; // assume 1 could be any valid double value
try{
float dest = doubleToFloat(source);
std::cout << "Source: (" << source << ") Dest: (" << dest << ")" << std::endl;
}
catch( std::exception& e )
{
std::cout << "Got exception error: " << e.what() << std::endl;
}
}
My primary interest is in adding error handling and safety to doubleToFloat(...), with various custom exceptions if needed.
As long as your floating-point types can store infinities (which is extremely likely), there is no possible undefined behavior. You can test std::numeric_limits<float>::has_infinity if you really want to be sure.
Use static_cast to silence the warning, and if you want to check for an overflow, you can do something like this:
template <typename T>
bool isInfinity(T f) {
return f == std::numeric_limits<T>::infinity()
|| f == -std::numeric_limits<T>::infinity();
}
float doubleToFloat(double num) {
float result = static_cast<float>(num);
if (isInfinity(result) && !isInfinity(num)) {
// overflow happened
}
return result;
}
Any double value that doesn't overflow will be converted either exactly or to one of the two nearest float values (probably the nearest). You can explicitly set the rounding direction with std::fesetround.
It depends on what you mean by "safely". There will most likely be a drop of precision in most cases. Do you want detect if this happens? Assert, or just know about it and notify the user?
A possible path of solution would be to static casting the double to a float, and then back to double, and compare the before and after. Equality is unlikely, but you could assert that the loss of precision is within your tolerance.
float doubleToFloat(double a_in, bool& ar_withinSpec, double a_tolerance)
{
auto reducedPrecision = static_cast<float>(a_in);
auto roundTrip = static_cast<double>(reducedPrecision);
ar_withinSpec = (roundTrip < a_tolerance);
return reducedPrecision;
}
I have code which has a lot of conversions from double to int . The code can be seen as
double n = 5.78;
int d = n; // double implicitly converted to a int
The implicit conversion from double to int is that of a truncation which means 5.78 will be saved as 5 . However it has been decided to change this behavior with custom rounding off .
One approach to such problem would be to have your own DOUBLE and INT data types and use conversion operators but alas my code is big and I am not allowed to do much changes . Another approach i thought of was to add 0.5 in each of the numbers but alas the code is big and i was changing too much .
What can be a simple approach to change double to int conversion behaviour which impact the whole code.
You can use uniform initialization syntax to forbid narrowing conversions:
double a;
int b{a}; // error
If you don't want that, you can use std::round function (or its sisters std::ceil/std::floor/std::trunc):
int b = std::round(a);
If you want minimal diff changes, here's what you can do. Please note, though, that this is a bad solution (if it can be named that), and much more likely leaving you crashing and burning due to undefined behavior than actually solving real problems.
Define your custom Int type that handles conversions the way you want it to:
class MyInt
{
//...
};
then evilly replace each occurence of int with MyInt with the help of preprocessor black magic:
#define int MyInt
Problems:
if you accidentally change definitions in the standard library - you're in the UB-land
if you change the return type of main - you're in the UB-land
if you change the definition of a function but not it's forward declarations - you're in the UB/linker error land. Or in the silently-calling-different-overload-land.
probably more.
Do something like this:
#include <iostream>
using namespace std;
int myConvert (double rhs)
{
int answer = (int)rhs; //do something fancier here to meet your needs
return answer;
}
int main()
{
double n = 5.78;
int d = myConvert(n);
cout << "d = " << d << endl;
return 0;
}
You can make myConvert as fancy as you want. Otherwise, you could define your own class for int (e.g. myInt class) and overload the = operator to do the right conversion.
I know that C & C++ are different languages standardized by different committees.
I know that like C efficiency has been a major design goal for C++ from the beginning. So, I think if any feature doesn't incur any runtime overhead & if it is efficient then it should be added into the language. The C99 standard has some very useful & efficient features and one of them is compound literals. I was reading about compiler literals here.
Following is a program that shows the use of compound literals.
#include <stdio.h>
// Structure to represent a 2D point
struct Point
{
int x, y;
};
// Utility function to print a point
void printPoint(struct Point p)
{
printf("%d, %d", p.x, p.y);
}
int main()
{
// Calling printPoint() without creating any temporary
// Point variable in main()
printPoint((struct Point){2, 3});
/* Without compound literal, above statement would have
been written as
struct Point temp = {2, 3};
printPoint(temp); */
return 0;
}
So, due to the use of compound literals there is no creation of an extra object of type struct Point as mentioned in the comments. So, isn't it efficient because it avoids the need for an extra operation copying objects? So, why does C++ still not support this useful feature? Are there any problems with compound literals?
I know that some compilers like g++ support compound literals as an extension but it usually leads to unportable code & that code isn't strictly standard conforming. Is there any proposal to add this feature to C++ also? If C++ doesn't support any feature of C there must be some reason behind it & I want to know that reason.
I think that there is no need for compound literals in C++, because in some way, this functionality is already covered by its OOP capabilities (objects, constructors and so on).
You program may be simply rewritten in C++ as:
#include <cstdio>
struct Point
{
Point(int x, int y) : x(x), y(y) {}
int x, y;
};
void printPoint(Point p)
{
std::printf("%d, %d", p.x, p.y);
}
int main()
{
printPoint(Point(2, 3)); // passing an anonymous object
}
I am looking for a solution using the C++03 standard (I am constrained to using this version of the standard for several years yet). Solutions for C++11 are also welcome, but will not be "accepted" as the answer to this question.
What is a simple, concise way that I can represent a set of related constant floating point values as a single type (similar to an enum) to ensure type-safety without incurring significant overhead and still allow me to operate on the values as floats directly?
The end result is that I would like to be able to do something like the following:
enum FloatingPointEnum
{
VALUE1 = 0.1234f,
...
VALUEN = 0.6789f
};
float SomeFunction(FloatingPointEnum value)
{
float new_value;
/* perform some operation using "value" to calculate "new_value" */
new_value = static_cast<float>(value); // <- a simplistic example
return new_value;
}
While I can think of several solutions, none of them are as clean/simple/straightforward as I would like and I figure that someone must already have an elegant solution to this problem (yet I cannot seem to find one in my searching).
EDIT:
I would like the following call to SomeFunction with a value that is not specified directly as a value from the enumerated type to fail to compile:
float nonEnumeratedValue = 5.0f
SomeFunction(nonEnumeratedValue);
someone must already have an elegant solution to this problem
There are lots of problems that have no elegant solution (and many that have no solution at all). What makes you think this problem has one? The closest you can get is to use a wrapper class.
class FloatingPointEnum {
float f;
FloatingPointEnum(float arg) : f(arg) {}
public:
static const FloatingPointEnum Value1;
static const FloatingPointEnum Value2;
operator float() const { return f; }
};
const FloatingPointEnum FloatingPointEnum::Value1(0.1234f);
const FloatingPointEnum FloatingPointEnum::Value2(0.6789f);
A possible alternative solution, not always applicable but very clean, is to use fixed precision.
Lets imagine you have you enum containing some distance in meters
enum DistancesMeter{
A = 0.25,
b = 0.05,
};
then you may simply switch to use mm
enum DistancesMM{
A = 250,
b = 50,
};
In C++11 you can use constexpr to achieve what you want.
constexpr - specifies that the value of a variable or function can appear in constant expressions
http://en.cppreference.com/w/cpp/language/constexpr
With constexpr you define a compile-time constant. This only works for literal types, such as float. Since at the same time we want
float nonEnumeratedValue = 5.0f;
SomeFunction(nonEnumeratedValue);
to fail, we cannot use a simple typedef. Instead we use Boost’s BOOST_STRONG_TYPEDEF.
#include <boost/serialization/strong_typedef.hpp>
BOOST_STRONG_TYPEDEF(float, FloatingPointEnum);
constexpr float VALUE1 = 0.1234f;
constexpr float VALUEN = 0.6789f;
float SomeFunction(FloatingPointEnum value)
{
float new_value;
/* perform some operation using "value" to calculate "new_value" */
new_value = static_cast<float>(value); // <- a simplistic example
return new_value;
}
Now you can call the function only with instances of FloatingPointEnum. Unfortunately, the instantiation syntax is not so nice anymore
FloatingPointEnum f {VALUEN};
Alternatively, you can simply use the D programming language, where floating point enums are supported and the following code works as expected:
enum FloatingPointEnum
{
VALUE1 = 0.1234f,
//...
VALUEN = 0.6789f
};
float SomeFunction(FloatingPointEnum value)
{
float new_value;
new_value = value; // No cast needed, welcome to D!
return new_value;
}
Calling SomeFunction with a float results in
Error: function test.SomeFunction (FloatingPointEnum value) is not callable using argument types (float)