Skip to content

Commit d36a9a1

Browse files
authored
Returned int128 library (#312)
1 parent 32e124e commit d36a9a1

19 files changed

+3549
-0
lines changed

library/cpp/CMakeLists.txt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,10 @@ add_subdirectory(uri)
5858
add_subdirectory(yson)
5959
add_subdirectory(yt)
6060

61+
if (YDB_SDK_TESTS)
62+
add_subdirectory(int128)
63+
endif()
64+
6165
if (CMAKE_SYSTEM_PROCESSOR STREQUAL "x86_64" OR CMAKE_SYSTEM_PROCESSOR STREQUAL "AMD64")
6266
add_subdirectory(cpuid_check)
6367
endif()

library/cpp/int128/CMakeLists.txt

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
_ydb_sdk_add_library(int128)
2+
3+
target_sources(int128
4+
PRIVATE
5+
int128.cpp
6+
)
7+
8+
target_link_libraries(int128
9+
PUBLIC
10+
yutil
11+
)

library/cpp/int128/README.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
https://st.yandex-team.ru/IGNIETFERRO-697
2+
3+
(Объединение разрозненных по Аркадии библиотек для поддержки 128-битного целого)
4+
5+
Идея классов ui128 / i128 в том, чтобы они работали так, как будто это компиляторные интовые типы.
6+
Т.е. у этих классов не должно быть публичных функций типа ui128::GetHigh(), конструкторов из нескольких параметров и так далее.

library/cpp/int128/int128.cpp

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
#include "int128.h"
2+
3+
#include <tuple>
4+
5+
IOutputStream& operator<<(IOutputStream& out, const ui128& other) {
6+
// see http://stackoverflow.com/questions/4361441/c-print-a-biginteger-in-base-10
7+
// and http://stackoverflow.com/questions/8023414/how-to-convert-a-128-bit-integer-to-a-decimal-ascii-string-in-c
8+
int d[39] = {0};
9+
int i;
10+
int j;
11+
for (i = 63; i > -1; i--) {
12+
if ((other.High_ >> i) & 1)
13+
++d[0];
14+
for (j = 0; j < 39; j++)
15+
d[j] *= 2;
16+
for (j = 0; j < 38; j++) {
17+
d[j + 1] += d[j] / 10;
18+
d[j] %= 10;
19+
}
20+
}
21+
for (i = 63; i > -1; i--) {
22+
if ((other.Low_ >> i) & 1)
23+
++d[0];
24+
if (i > 0)
25+
for (j = 0; j < 39; j++)
26+
d[j] *= 2;
27+
for (j = 0; j < 38; j++) {
28+
d[j + 1] += d[j] / 10;
29+
d[j] %= 10;
30+
}
31+
}
32+
for (i = 38; i > 0; i--)
33+
if (d[i] > 0)
34+
break;
35+
for (; i > -1; i--)
36+
out << static_cast<char>('0' + d[i]);
37+
38+
return out;
39+
}
40+
41+
void TSerializer<ui128>::Save(IOutputStream* out, const ui128& Number) {
42+
::Save(out, GetHigh(Number));
43+
::Save(out, GetLow(Number));
44+
}
45+
46+
void TSerializer<ui128>::Load(IInputStream* in, ui128& Number) {
47+
ui64 High;
48+
ui64 Low;
49+
::Load(in, High);
50+
::Load(in, Low);
51+
Number = ui128(High, Low);
52+
}
53+
54+
IOutputStream& operator<<(IOutputStream& out, const i128& other)
55+
{
56+
if (other >= 0) {
57+
out << ui128{other};
58+
} else {
59+
out << '-' << ui128{-other};
60+
}
61+
return out;
62+
}

0 commit comments

Comments
 (0)