d06 ex00 ajout qq tests avec limits des floats
This commit is contained in:
@@ -34,7 +34,8 @@ SRCS = main.cpp \
|
||||
checkChar.cpp \
|
||||
checkInt.cpp \
|
||||
checkFloat.cpp \
|
||||
checkDouble.cpp
|
||||
checkDouble.cpp \
|
||||
toTypes.cpp
|
||||
|
||||
D_HEADERS = .
|
||||
HEADERS = convert.h
|
||||
|
||||
BIN
d06/ex00/a.out
Executable file
BIN
d06/ex00/a.out
Executable file
Binary file not shown.
BIN
d06/ex00/convert
BIN
d06/ex00/convert
Binary file not shown.
@@ -17,6 +17,14 @@ bool checkInt(std::string str);
|
||||
bool checkFloat(std::string str);
|
||||
bool checkDouble(std::string str);
|
||||
|
||||
// templates
|
||||
// see : https://isocpp.org/wiki/faq/templates#templates-defn-vs-decl
|
||||
template <typename T> void toChar(T value);
|
||||
template <typename T> void toInt(T value);
|
||||
template <typename T> void toFloat(T value);
|
||||
template <typename T> void toDouble(T value);
|
||||
//template <typename T> void printDot(T value);
|
||||
|
||||
#define MAX_INT "2147483647"
|
||||
#define MIN_INT "-2147483648"
|
||||
#define MAX_INT_1 "2147483648"
|
||||
@@ -24,6 +32,7 @@ bool checkDouble(std::string str);
|
||||
#define INT_MAX_LENGTH 10
|
||||
#define MAX_FLOAT_INT_PRECISION "16777216"
|
||||
#define MAX_FLOAT "340282346638528859811704183484516925440"
|
||||
#define MIN_FLOAT "-340282346638528859811704183484516925440"
|
||||
#define FLOAT_MAX_LENGTH 39
|
||||
#define MAX_DOUBLE "179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858368"
|
||||
#define DOUBLE_MAX_LENGTH 309
|
||||
@@ -49,6 +58,7 @@ bool checkDouble(std::string str);
|
||||
#define MAX_F_4 "340282346638528859811704183484516925444"
|
||||
#define MAX_F_5 "340282346638528859811704183484516925445"
|
||||
#define MAX_F_6 "340282346638528859811704183484516925446"
|
||||
#define MAX_F_N "340282346638528897590636046441678635008"
|
||||
#define MIN_DOUBLE "-179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858368"
|
||||
#define MAX_D__1 "179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858367"
|
||||
#define MAX_D__2 "179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858366"
|
||||
|
||||
@@ -180,6 +180,7 @@ int main(int ac, char **av) {
|
||||
convert(MAX_F_4".0f");
|
||||
convert(MAX_F_5".0f");
|
||||
convert(MAX_F_6".0f");
|
||||
convert(MAX_F_N".0f");
|
||||
//double
|
||||
convert("0.0");
|
||||
convert("-4.2");
|
||||
@@ -213,6 +214,7 @@ int main(int ac, char **av) {
|
||||
convert(MAX_F_4".0");
|
||||
convert(MAX_F_5".0");
|
||||
convert(MAX_F_6".0");
|
||||
convert(MAX_F_N".0");
|
||||
convert(MAX_DOUBLE".0");
|
||||
convert(MIN_DOUBLE".0");
|
||||
convert(MAX_D__1".0");
|
||||
|
||||
@@ -2,29 +2,11 @@
|
||||
|
||||
void fromDouble(double value) {
|
||||
// char
|
||||
std::cout << std::setw(7) << std::left << "char";
|
||||
if (value < 0 || value > std::numeric_limits<char>::max())
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else if (!isprint(value))
|
||||
std::cout << B_RED << "non displayable" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<char>(value) << RESET "\n";
|
||||
|
||||
toChar(value);
|
||||
// int
|
||||
std::cout << std::setw(7) << std::left << "int";
|
||||
if (value < std::numeric_limits<int>::min()
|
||||
|| value > std::numeric_limits<int>::max() )
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<int>(value) << RESET "\n";
|
||||
|
||||
toInt(value);
|
||||
// float
|
||||
std::cout << std::setw(7) << std::left << "float";
|
||||
if (value < std::numeric_limits<float>::min()
|
||||
|| value > std::numeric_limits<float>::max() )
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<double>(value) << RESET "\n";
|
||||
toFloat(value);
|
||||
}
|
||||
|
||||
bool isDouble(std::string str) {
|
||||
@@ -57,8 +39,11 @@ bool checkDouble(std::string str) {
|
||||
if (!isDouble(str))
|
||||
return false;
|
||||
|
||||
std::istringstream(str) >> d;
|
||||
std::cout << B_CYAN << d << B_YELLOW " double" RESET "\n";
|
||||
// std::istringstream(str) >> d;
|
||||
d = strtod(str.c_str(), NULL);
|
||||
std::cout << std::fixed << B_CYAN << d;
|
||||
// printDot(d);
|
||||
std::cout << B_YELLOW " double" RESET "\n";
|
||||
fromDouble(d);
|
||||
|
||||
return true;
|
||||
|
||||
@@ -1,29 +1,15 @@
|
||||
#include "convert.h"
|
||||
|
||||
void fromFloat(float value) {
|
||||
static void fromFloat(float value) {
|
||||
// char
|
||||
std::cout << std::setw(7) << std::left << "char";
|
||||
if (value < 0 || value > std::numeric_limits<char>::max())
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else if (!isprint(value))
|
||||
std::cout << B_RED << "non displayable" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<char>(value) << RESET "\n";
|
||||
|
||||
toChar(value);
|
||||
// int
|
||||
std::cout << std::setw(7) << std::left << "int";
|
||||
if (value < std::numeric_limits<int>::min()
|
||||
|| value > std::numeric_limits<int>::max() )
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<int>(value) << RESET "\n";
|
||||
|
||||
toInt(value);
|
||||
// double
|
||||
std::cout << std::setw(7) << std::left << "double";
|
||||
std::cout << B_CYAN << static_cast<double>(value) << RESET "\n";
|
||||
toDouble(value);
|
||||
}
|
||||
|
||||
bool isFloat(std::string str) {
|
||||
static bool isFloat(std::string str) {
|
||||
size_t l;
|
||||
size_t l2;
|
||||
|
||||
@@ -53,8 +39,11 @@ bool checkFloat(std::string str) {
|
||||
if (!isFloat(str))
|
||||
return false;
|
||||
|
||||
std::istringstream(str) >> f;
|
||||
std::cout << B_CYAN << f << B_YELLOW " float" RESET "\n";
|
||||
// std::istringstream(str) >> f;
|
||||
f = strtod(str.c_str(), NULL);
|
||||
std::cout << std::fixed << B_CYAN << f;
|
||||
// printDot(f);
|
||||
std::cout << "f" << B_YELLOW " float" RESET "\n";
|
||||
fromFloat(f);
|
||||
|
||||
return true;
|
||||
|
||||
@@ -2,21 +2,11 @@
|
||||
|
||||
void fromInt(int value) {
|
||||
// char
|
||||
std::cout << std::setw(7) << std::left << "char";
|
||||
if (value < 0 || value > std::numeric_limits<char>::max())
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else if (!isprint(value))
|
||||
std::cout << B_RED << "non displayable" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<char>(value) << RESET "\n";
|
||||
|
||||
toChar(value);
|
||||
// float
|
||||
std::cout << std::setw(7) << std::left << "float" << B_CYAN
|
||||
<< static_cast<float>(value) << RESET "\n";
|
||||
|
||||
toFloat(value);
|
||||
// double
|
||||
std::cout << std::setw(7) << std::left << "double" << B_CYAN
|
||||
<< static_cast<double>(value) << RESET "\n";
|
||||
toDouble(value);
|
||||
}
|
||||
|
||||
bool isInt(std::string str) {
|
||||
|
||||
90
d06/ex00/srcs/toTypes.cpp
Normal file
90
d06/ex00/srcs/toTypes.cpp
Normal file
@@ -0,0 +1,90 @@
|
||||
#include "convert.h"
|
||||
#include <cfloat>
|
||||
|
||||
// tried to check for NaN and INF
|
||||
//static bool is_inf_pos( float a ) { return ( *(((long*)(&a))+1) & 0xFFFFFFFFU ) == 0x7F800000U; }
|
||||
//static bool is_inf_neg( float a ) { return ( *(((long*)(&a))+1) & 0xFFFFFFFFU ) == 0xFF800000U; }
|
||||
//static bool is_nan( float a ) { return (( *(((long*)(&a))+1) & 0x7FF80000L ) == 0x7FF800000L); }
|
||||
|
||||
// https://isocpp.org/wiki/faq/templates#templates-defn-vs-decl
|
||||
template <typename T>
|
||||
void toChar(T value) {
|
||||
std::cout << std::setw(7) << std::left << "char";
|
||||
// if (value < 0 || value > std::numeric_limits<char>::max())
|
||||
if (!(value >= 0 && value <= std::numeric_limits<char>::max()))
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
else if (!isprint(value))
|
||||
std::cout << B_RED << "non displayable" << RESET "\n";
|
||||
else
|
||||
std::cout << B_CYAN << static_cast<char>(value) << RESET "\n";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void toInt(T value) {
|
||||
std::cout << std::setw(7) << std::left << "int";
|
||||
// if (value < std::numeric_limits<int>::min()
|
||||
// || value > std::numeric_limits<int>::max() )
|
||||
if (! (value <= std::numeric_limits<int>::max()
|
||||
&& value >= std::numeric_limits<int>::min()) )
|
||||
{
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
return ;
|
||||
}
|
||||
std::cout << B_CYAN << static_cast<int>(value) << RESET "\n";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void toFloat(T value) {
|
||||
std::cout << std::setw(7) << std::left << "float";
|
||||
// tricks to check if is nan and infinity
|
||||
// see : https://www.jacksondunstan.com/articles/983
|
||||
// and : https://stackoverflow.com/questions/2249110/how-do-i-make-a-portable-isnan-isinf-function
|
||||
if (!((value * 0) != 0))
|
||||
// min() ne renvoit que 0, il faut utiliser lowest() (c++11) ou -max()
|
||||
// https://stackoverflow.com/questions/17070351/why-does-numeric-limitsmin-return-a-negative-value-for-int-but-positive-values
|
||||
// https://en.cppreference.com/w/cpp/types/numeric_limits/min
|
||||
if (! (value <= std::numeric_limits<float>::max()
|
||||
&& value >= -(std::numeric_limits<float>::max())) )
|
||||
{
|
||||
std::cout << B_RED << "impossible" << RESET "\n";
|
||||
return ;
|
||||
}
|
||||
std::cout << B_CYAN << std::fixed << static_cast<float>(value);
|
||||
// printDot(value);
|
||||
std::cout << "f" << RESET "\n";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void toDouble(T value) {
|
||||
std::cout << std::setw(7) << std::left << "double" << B_CYAN
|
||||
<< std::fixed << static_cast<double>(value);
|
||||
// printDot(value);
|
||||
std::cout << RESET "\n";
|
||||
}
|
||||
|
||||
//template <typename T>
|
||||
//void printDot(T value) {
|
||||
// std::ostringstream ostr;
|
||||
// ostr << value;
|
||||
// if (ostr.str().compare("inf")
|
||||
// && ostr.str().compare("-inf")
|
||||
// && ostr.str().compare("nan"))
|
||||
// if ((ostr.str().find('.')) == std::string::npos)
|
||||
// std::cout << ".0";
|
||||
//}
|
||||
|
||||
template void toChar<int>(int);
|
||||
template void toChar<float>(float);
|
||||
template void toChar<double>(double);
|
||||
|
||||
template void toInt<float>(float);
|
||||
template void toInt<double>(double);
|
||||
|
||||
template void toFloat<int>(int);
|
||||
template void toFloat<double>(double);
|
||||
|
||||
template void toDouble<int>(int);
|
||||
template void toDouble<float>(float);
|
||||
|
||||
//template void printDot<float>(float);
|
||||
//template void printDot<double>(double);
|
||||
36
d06/ex00/test_float.cpp
Normal file
36
d06/ex00/test_float.cpp
Normal file
@@ -0,0 +1,36 @@
|
||||
#include <iostream>
|
||||
#include <limits>
|
||||
#include <cfloat>
|
||||
#include <cmath>
|
||||
|
||||
#define MAX_INT 2147483647
|
||||
#define MIN_INT -2147483648
|
||||
#define MAX_FLOAT 340282346638528859811704183484516925440.0f
|
||||
#define MIN_FLOAT -340282346638528859811704183484516925440.0f
|
||||
|
||||
void isFloat(double d) {
|
||||
if (! (d <= std::numeric_limits<float>::max()
|
||||
&& d >= std::numeric_limits<float>::min()) )
|
||||
{
|
||||
std::cout << d << "is outside range of floats\n";
|
||||
return ;
|
||||
}
|
||||
std::cout << std::fixed << static_cast<float>(d) << "\n";
|
||||
}
|
||||
|
||||
int main() {
|
||||
|
||||
double d;
|
||||
double d2;
|
||||
|
||||
d = std::numeric_limits<float>::max();
|
||||
std::cout << std::fixed << d << "\n";
|
||||
d2 = std::nextafter(d, DBL_MAX);
|
||||
std::cout << std::fixed << d2 << "\n";
|
||||
// isFloat(MAX_FLOAT);
|
||||
// d = std::numeric_limits<float>::lowest();
|
||||
// std::cout << std::fixed << d << "\n";
|
||||
// isFloat(d);
|
||||
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user