Próbuję dodać dwie liczby 32-bitowe, ale używając do tego intów tylko 16-bitowych:
#include <cstdint>
#include <cstdio>
#include <bitset>
#include<iostream>
uint16_t add_hi(uint16_t a, uint16_t b)
{
uint16_t a_lo = (uint8_t)a;
uint16_t a_hi = a >> 8;
uint16_t b_lo = (uint8_t)b;
uint16_t b_hi = b >> 8;
uint16_t a_b_carry_low = (a_lo + b_lo) >> 8;
uint16_t a_b_carry_high = (a_hi + b_hi) >> 8;
uint16_t addhi = a_b_carry_low + a_b_carry_high;
if (addhi > 1) { addhi = 1; }
return addhi;
}
int main()
{
uint32_t r = 2135768218;
std::cout << r << "\n";
uint16_t a_low = (uint16_t)r;
uint16_t a_hi = r >> 16;
uint16_t b_low = (uint16_t)r;
uint16_t b_hi = r >> 16;
uint16_t wynik_hi = add_hi(a_low, b_low) + a_hi + b_hi;
uint16_t wynik_low = a_low + b_low;
uint32_t wynik = (wynik_hi << 16) | wynik_low;
uint32_t wynik_1 = r + r;
std::cout << wynik << " " << wynik_1 << "\n";
}
Wynik jest zgodny z prawdziwym wynikiem wynik_1 dla wielu liczb, ale nie dla 2135768218 i kilku innych. Funkcja add_hi służy do wyznaczenia górnego bitu z dodawania dolnych części naszych dwóch 32-bitowych liczb. Następnie obliczam górną część wyniku wynik_hi i dolną wynik_low, która jest trywialna do wyznaczenia.
Co robię źle?