C++ floating point to integer type conversions

C++Floating PointIntegerType ConversionTypecast Operator

C++ Problem Overview


What are the different techniques used to convert float type of data to integer in C++?

#include <iostream>

using namespace std;
struct database {
  int id, age;
  float salary;
};

int main() {
  struct database employee;
  employee.id = 1;
  employee.age = 23;
  employee.salary = 45678.90;
  /*
     How can i print this value as an integer
     (with out changing the salary data type in the declaration part) ?
   */
  cout << endl << employee.id << endl << employee.
  age << endl << employee.salary << endl;
  return 0;
}

C++ Solutions


Solution 1 - C++

What you are looking for is 'type casting'. typecasting (putting the type you know you want in brackets) tells the compiler you know what you are doing and are cool with it. The old way that is inherited from C is as follows.

float var_a = 9.99;
int   var_b = (int)var_a;

If you had only tried to write

int var_b = var_a;

You would have got a warning that you can't implicitly (automatically) convert a float to an int, as you lose the decimal.

This is referred to as the old way as C++ offers a superior alternative, 'static cast'; this provides a much safer way of converting from one type to another. The equivalent method would be (and the way you should do it)

float var_x = 9.99;
int   var_y = static_cast<int>(var_x);

This method may look a bit more long winded, but it provides much better handling for situations such as accidentally requesting a 'static cast' on a type that cannot be converted. For more information on the why you should be using static cast, see this question.

Solution 2 - C++

Normal way is to:

float f = 3.4;
int n = static_cast<int>(f);

Solution 3 - C++

Size of some float types may exceed the size of int. This example shows a safe conversion of any float type to int using the int safeFloatToInt(const FloatType &num); function:

#include <iostream>
#include <limits>
using namespace std;

template <class FloatType>
int safeFloatToInt(const FloatType &num) {
   //check if float fits into integer
   if ( numeric_limits<int>::digits < numeric_limits<FloatType>::digits) {
      // check if float is smaller than max int
      if( (num < static_cast<FloatType>( numeric_limits<int>::max())) &&
          (num > static_cast<FloatType>( numeric_limits<int>::min())) ) {
         return static_cast<int>(num); //safe to cast
      } else {
        cerr << "Unsafe conversion of value:" << num << endl;
        //NaN is not defined for int return the largest int value
        return numeric_limits<int>::max();
      }
   } else {
      //It is safe to cast
      return static_cast<int>(num);
   }
}
int main(){
   double a=2251799813685240.0;
   float b=43.0;
   double c=23333.0;
   //unsafe cast
   cout << safeFloatToInt(a) << endl;
   cout << safeFloatToInt(b) << endl;
   cout << safeFloatToInt(c) << endl;
   return 0;
}

Result:

Unsafe conversion of value:2.2518e+15
2147483647
43
23333

Solution 4 - C++

For most cases (long for floats, long long for double and long double):

long a{ std::lround(1.5f) }; //2l
long long b{ std::llround(std::floor(1.5)) }; //1ll

Solution 5 - C++

Check out the boost NumericConversion library. It will allow to explicitly control how you want to deal with issues like overflow handling and truncation.

Solution 6 - C++

I believe you can do this using a cast:

float f_val = 3.6f;
int i_val = (int) f_val;

Solution 7 - C++

the easiest technique is to just assign float to int, for example:

int i;
float f;
f = 34.0098;
i = f;

this will truncate everything behind floating point or you can round your float number before.

Solution 8 - C++

One thing I want to add. Sometimes, there can be precision loss. You may want to add some epsilon value first before converting. Not sure why that works... but it work.

int someint = (somedouble+epsilon);

Solution 9 - C++

This is one way to convert IEEE 754 float to 32-bit integer if you can't use floating point operations. It has also a scaler functionality to include more digits to the result. Useful values for scaler are 1, 10 and 100.

#define EXPONENT_LENGTH 8
#define MANTISSA_LENGTH 23
// to convert float to int without floating point operations
int ownFloatToInt(int floatBits, int scaler) {
	int sign = (floatBits >> (EXPONENT_LENGTH + MANTISSA_LENGTH)) & 1;
	int exponent = (floatBits >> MANTISSA_LENGTH) & ((1 << EXPONENT_LENGTH) - 1);
	int mantissa = (floatBits & ((1 << MANTISSA_LENGTH) - 1)) | (1 << MANTISSA_LENGTH);
	int result = mantissa * scaler; // possible overflow
	exponent -= ((1 << (EXPONENT_LENGTH - 1)) - 1); // exponent bias
	exponent -= MANTISSA_LENGTH; // modify exponent for shifting the mantissa
	if (exponent <= -(int)sizeof(result) * 8) {
		return 0; // underflow
	}
	if (exponent > 0) {
		result <<= exponent; // possible overflow
	} else {
		result >>= -exponent;
	}
	if (sign) result = -result; // handle sign
	return result;
}

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionmoalaView Question on Stackoverflow
Solution 1 - C++thecoshmanView Answer on Stackoverflow
Solution 2 - C++NaveenView Answer on Stackoverflow
Solution 3 - C++zoli2kView Answer on Stackoverflow
Solution 4 - C++Roman GorislavskiView Answer on Stackoverflow
Solution 5 - C++simongView Answer on Stackoverflow
Solution 6 - C++SeidrView Answer on Stackoverflow
Solution 7 - C++sanjuroView Answer on Stackoverflow
Solution 8 - C++asdacapView Answer on Stackoverflow
Solution 9 - C++Harri LuomaView Answer on Stackoverflow