GfG QA is closing soon... Please refer PRACTICE or GfG now on wards !!

Return the fraction as string

Given two integers representing the numerator and denominator of a fraction, return the fraction in string format.

If the fractional part is repeating, enclose the repeating part in parentheses.

Example :

Given numerator = 1, denominator = 2, return "0.5"
Given numerator = 2, denominator = 1, return "2"
Given numerator = 2, denominator = 3, return "0.(6)"
asked Oct 8, 2015 by Swanky

1 Answer

When does the fractional part repeat ?

Lets simulate the process of converting fraction to decimal. Lets look at the part where we have already figured out the integer part which is floor(numerator / denominator).
Now we are left with ( remainder = numerator%denominator ) / denominator.
If we remember the process of converting to decimal, at each step we do the following :

1) multiply the remainder by 10,
2) append remainder / denominator to your decimals
3) remainder = remainder % denominator.

At any moment, if your remainder becomes 0, we are done.

However, there is a problem with recurring decimals. For example if we look at 1/3, the remainder never becomes 0.

Notice one more important thing.
If we start with remainder = R at any point with denominator d, we will always get the same sequence of digits.
So, if our remainder repeats at any point of time, we know that the digits between the last occurrence of R will keep repeating.

 

#include<bits/stdc++.h>
using namespace std;
 
string solve(int numerator, int denominator) {
 
	int64_t n = numerator, d = denominator;
    // zero numerator
    if (n == 0) return "0";
 
    string res;
    // determine the sign
    if (n < 0 ^ d < 0) res += '-';
 
    // remove sign of operands
    n = abs(n), d = abs(d);
 
	// append integral part
    res += to_string((n / d));
 
    // in case no fractional part
    if (n % d == 0) return res;
 
	res += '.';
 
    unordered_map<int, int> map;
 
    // simulate the division process
    for (int64_t r = n % d; r; r %= d) {
 
        // meet a known remainder
        // so we reach the end of the repeating part
        if (map.find(r) != map.end()) {
            // insert '(' at the start position where we first saw the remainder
            res.insert(map[r], 1, '(');
            res += ')';
            break;
        }
 
        // the remainder is first seen
        // remember the current position for it
        map[r] = res.size();
 
        r *= 10;
 
        // append the quotient digit
        res.push_back((char)('0' + (r / d)));
    }
 
    return res;    
}
 
int main() {
 
	cout << solve(1, 2) << endl;
	return 0;
}
 

http://ideone.com/eKrb3t

answered Oct 8, 2015 by Gaurav
...