How come map() function is proper and correct? What is the idea behind it?

J-M-L:
I disagree with that. as floating points in an arduino are not very precise, not respecting basic maths laws depending on the order in which you perfrom your math for some numbers you bring your own set of issues with float. And then it's slow which in some cases is a problem too. Remember You are not running your code on a great modern CPU with dedicated floating point computation engine. I try to stay away from float as much as I can in my code because ultimately your output or input reading are integer.

It's not that they disrespect basic math laws, but floats have their own truncation issues. They are not magical infinite precision numbers capable of perfectly representing the value of any real number. They aren't even capable of perfectly representing all rational numbers.

The standard is IEEE-754. For a 32-bit float it sets aside a fixed number of bits (23) for the mantissa, 1 sign bit, and the rest (8) for the signed exponent. Because the mantissa is a fixed number of bits, it is only capable of perfect representing binary fractions, ie fractions where the denominator is a power of 2. Even simple fractions like 1/5 cannot be prefectly represented as a float because when converted to their binary representation the mantissa will have a repeating, non-terminating pattern, much like 1/3 or 1/7 have in their decimal representation.

Generally speaking, if the prime factors of the denominator of a rational number contain any numbers that are not prime factors of the number system's radix, that value cannot be represented in that number system in a finite number of digits. It will have an infinite repeating sequence.

The size of the mantissa also limits the depth of precision you can have, even if you do have a binary fraction. You could not represent a number like (20 + 2-40), because the mantissa is not large enough to hold that much precision. The 2-40 term will be truncated.

The limited size of the exponent field also places a constraint on the size of the numbers. 2200 or 2-200 have an exponent outside of the range the exponent field can hold, and cannot be represented in a 32-bit float.

Because of the truncation issues that happen when you do divisions by numbers that are not powers of 2, it is recommended to never compare floating-point numbers using equality (==), you are recommended to subtract them and test that the absolute value of the difference is smaller than some tolerance value that you have to come up with.

TLDR; "Throwing money at the problem" by converting all your types to float without considering their own set of issues might not magically fix all your problems. Yes, the rounding behavior is different than integers, but that does not mean it is better. The current map() function, operating on integral types is perfectly functional for all the examples that have been brought up in this thread if you are willing to use it properly and not just bang your head against a wall about how it doesn't work in exactly the way you think it should work.