2

Can anyone explain how the math in this contract works?

    pragma solidity =0.5.16;

// a library for handling binary fixed point numbers (https://en.wikipedia.org/wiki/Q_(number_format))

// range: [0, 2**112 - 1]
// resolution: 1 / 2**112

library UQ112x112 {
    uint224 constant Q112 = 2**112;

    // encode a uint112 as a UQ112x112
    function encode(uint112 y) internal pure returns (uint224 z) {
        z = uint224(y) * Q112; //never overflows 
    }

    // divide a UQ112x112 by a uint112, returning a UQ112x112
    function uqdiv(uint224 x, uint112 y) internal pure returns (uint224 z) {
        z = x / uint224(y);
    }
}

I am not able to understand how these two functions helps with fractions.

Thank you.

Yilmaz
  • 35,338
  • 10
  • 157
  • 202
RɘN __
  • 53
  • 7
  • 1
    Interesting question, I dig deeper and found [this answer](https://ethereum.stackexchange.com/a/113336/76945) pretty useful to understand this library. – turboza Jun 17 '22 at 07:29

1 Answers1

0

I converted the library to a contract and make the functions public to be able to interact in Remix

contract UQ112x112 {
    uint224 constant Q112 = 2**112;

    function encode(uint112 y) public pure returns (uint224 z) {
        z = uint224(y) * Q112; //never overflows 
    }
    function uqdiv(uint224 x, uint112 y) public pure returns (uint224 z) {
        z = x / uint224(y);
    }
}
  • encode function

    function encode(uint112 y) internal pure returns (uint224 z) {
          z = uint224(y) * Q112; //never overflows 
      }
    

This will shift the input value y by 112 bits to the left, effectively encoding it as a uint224 value. 1 bit shifting is equal to multiplying the number by 2. If I call encode(1)

enter image description here

If you convert the return int value to binary here, you get this

10000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000

We are storing our input in uint224 without losing precision. In uniswap, prices are stored in uint224 so we are converting price input into the uin224

  • uqdiv function just a simple division operation

    function uqdiv(uint224 x, uint112 y) internal pure returns (uint224 z) {
       z = x / uint224(y);
    } 
    
Yilmaz
  • 35,338
  • 10
  • 157
  • 202