C/C++ counting the number of decimals?

后端 未结 13 1941
北荒
北荒 2020-12-06 16:04

Lets say that input from the user is a decimal number, ex. 5.2155 (having 4 decimal digits). It can be stored freely (int,double) etc.

Is there any

相关标签:
13条回答
  • 2020-12-06 16:35

    This is a robust C++ 11 implementation suitable for float and double types:

    #include <type_traits>
    #include <cstdlib>
    #include <cmath>
    
    template <typename T>
    std::enable_if_t<(std::is_floating_point<T>::value), std::size_t>
    decimal_places(T v)
    {
        std::size_t count = 0;
    
        v = std::abs(v);
    
        auto c = v - std::floor(v);
    
        T factor = 10;
    
        while (c > 0 && count < std::numeric_limits<T>::max_digits10)
        {
            c = v * factor;
    
            c = c - std::floor(c);
    
            factor *= 10;
    
            count++;
        }
    
        return count;
    }
    

    It throws the value away each iteration and instead keeps track of a power of 10 multiplier to avoid rounding issues building up.

    0 讨论(0)
  • 2020-12-06 16:37

    using the Scientific Notation format (to avoid rounding errors):

    #include <stdio.h>
    #include <string.h>
    
    /* Counting the number of decimals
     *
     * 1. Use Scientific Notation format
     * 2. Convert it to a string
     * 3. Tokenize it on the exp sign, discard the base part
     * 4. convert the second token back to number
    */
    
    int main(){
    
       int counts;
       char *sign;
       char str[15];
       char *base;
       char *exp10;
       float real = 0.00001;
    
       sprintf (str, "%E",  real);
       sign= ( strpbrk ( str, "+"))? "+" : "-";
    
       base = strtok (str, sign);
       exp10 = strtok (NULL, sign);
    
       counts=atoi(exp10);
    
       printf("[%d]\n", counts);
    
       return 0;
    }
    

    [5]

    0 讨论(0)
  • 2020-12-06 16:38

    Once the number is converted from the user representation (string, OCR-ed gif file, whatever) into a floating point number, you are not dealing with the same number necessarily. So the strict, not very useful answer is "No".

    If (case A) you can avoid converting the number from the string representation, the problem becomes much easier, you only need to count the digits after the decimal point and subtract the number of trailing zeros.

    If you cannot do it (case B), then you need to make an assumption about the maximum number of decimals, convert the number back into string representation and round it to this maximum number using the round-to-even method. For example, if the user supplies 1.1 which gets represented as 1.09999999999999 (hypothetically), converting it back to string yields, guess what, "1.09999999999999". Rounding this number to, say, four decimal points gives you "1.1000". Now it's back to case A.

    0 讨论(0)
  • 2020-12-06 16:38

    I would suggest reading the value as a string, searching for the decimal point, and parsing the text before and after it as integers. No floating point or rounding errors.

    0 讨论(0)
  • 2020-12-06 16:42

    Years after the fight but as I have made my own solution in three lines :

    string number = "543.014";    
    size_t dotFound;
    stoi(number, &dotFound));
    string(number).substr(dotFound).size()
    

    Of course you have to test before if it is really a float (With stof(number) == stoi(number) for example)

    0 讨论(0)
  • 2020-12-06 16:43

    What do you mean "stored freely (int"? Once stored in an int, it has zero decimals left, clearly. A double is stored in a binary form, so no obvious or simple relation to "decimals" either. Why don't you keep the input as a string, just long enough to count those decimals, before sending it on to its final numeric-variable destination?

    0 讨论(0)
提交回复
热议问题