| 17327 | } |
| 17328 | |
| 17329 | inline void grisu2_round(char* buf, int len, std::uint64_t dist, std::uint64_t delta, |
| 17330 | std::uint64_t rest, std::uint64_t ten_k) |
| 17331 | { |
| 17332 | JSON_ASSERT(len >= 1); |
| 17333 | JSON_ASSERT(dist <= delta); |
| 17334 | JSON_ASSERT(rest <= delta); |
| 17335 | JSON_ASSERT(ten_k > 0); |
| 17336 | |
| 17337 | // <--------------------------- delta ----> |
| 17338 | // <---- dist ---------> |
| 17339 | // --------------[------------------+-------------------]-------------- |
| 17340 | // M- w M+ |
| 17341 | // |
| 17342 | // ten_k |
| 17343 | // <------> |
| 17344 | // <---- rest ----> |
| 17345 | // --------------[------------------+----+--------------]-------------- |
| 17346 | // w V |
| 17347 | // = buf * 10^k |
| 17348 | // |
| 17349 | // ten_k represents a unit-in-the-last-place in the decimal representation |
| 17350 | // stored in buf. |
| 17351 | // Decrement buf by ten_k while this takes buf closer to w. |
| 17352 | |
| 17353 | // The tests are written in this order to avoid overflow in unsigned |
| 17354 | // integer arithmetic. |
| 17355 | |
| 17356 | while (rest < dist |
| 17357 | && delta - rest >= ten_k |
| 17358 | && (rest + ten_k < dist || dist - rest > rest + ten_k - dist)) |
| 17359 | { |
| 17360 | JSON_ASSERT(buf[len - 1] != '0'); |
| 17361 | buf[len - 1]--; |
| 17362 | rest += ten_k; |
| 17363 | } |
| 17364 | } |
| 17365 | |
| 17366 | /*! |
| 17367 | Generates V = buffer * 10^decimal_exponent, such that M- <= V <= M+. |