#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <assert.h>
typedef struct {
uint32_t length;
uint64_t limit;
} String_Length_Table;
typedef union {
// UINT64_MAX is 20 bytes.
char view_8[21];
} Print_Buffer;
String_Length_Table string_length_table[65] = {
String_Length_Table { 1, UINT64_MAX },
String_Length_Table { 1, UINT64_MAX },
String_Length_Table { 1, UINT64_MAX },
String_Length_Table { 1, UINT64_MAX },
String_Length_Table { 1, 10 },
String_Length_Table { 2, UINT64_MAX },
String_Length_Table { 2, UINT64_MAX },
String_Length_Table { 2, 100 },
String_Length_Table { 3, UINT64_MAX },
String_Length_Table { 3, UINT64_MAX },
String_Length_Table { 3, 1000 },
String_Length_Table { 4, UINT64_MAX },
String_Length_Table { 4, UINT64_MAX },
String_Length_Table { 4, UINT64_MAX },
String_Length_Table { 4, 10000 },
String_Length_Table { 5, UINT64_MAX },
String_Length_Table { 5, UINT64_MAX },
String_Length_Table { 5, 100000 },
String_Length_Table { 6, UINT64_MAX },
String_Length_Table { 6, UINT64_MAX },
String_Length_Table { 6, 1000000 },
String_Length_Table { 7, UINT64_MAX },
String_Length_Table { 7, UINT64_MAX },
String_Length_Table { 7, UINT64_MAX },
String_Length_Table { 7, 10000000 },
String_Length_Table { 8, UINT64_MAX },
String_Length_Table { 8, UINT64_MAX },
String_Length_Table { 8, 100000000 },
String_Length_Table { 9, UINT64_MAX },
String_Length_Table { 9, UINT64_MAX },
String_Length_Table { 9, 1000000000 },
String_Length_Table { 10, UINT64_MAX },
String_Length_Table { 10, UINT64_MAX },
String_Length_Table { 10, UINT64_MAX },
String_Length_Table { 10, 10000000000 },
String_Length_Table { 11, UINT64_MAX },
String_Length_Table { 11, UINT64_MAX },
String_Length_Table { 11, 100000000000 },
String_Length_Table { 12, UINT64_MAX },
String_Length_Table { 12, UINT64_MAX },
String_Length_Table { 12, 1000000000000 },
String_Length_Table { 13, UINT64_MAX },
String_Length_Table { 13, UINT64_MAX },
String_Length_Table { 13, UINT64_MAX },
String_Length_Table { 13, 10000000000000 },
String_Length_Table { 14, UINT64_MAX },
String_Length_Table { 14, UINT64_MAX },
String_Length_Table { 14, 100000000000000 },
String_Length_Table { 15, UINT64_MAX },
String_Length_Table { 15, UINT64_MAX },
String_Length_Table { 15, 1000000000000000 },
String_Length_Table { 16, UINT64_MAX },
String_Length_Table { 16, UINT64_MAX },
String_Length_Table { 16, UINT64_MAX },
String_Length_Table { 16, 10000000000000000 },
String_Length_Table { 17, UINT64_MAX },
String_Length_Table { 17, UINT64_MAX },
String_Length_Table { 17, 100000000000000000 },
String_Length_Table { 18, UINT64_MAX },
String_Length_Table { 18, UINT64_MAX },
String_Length_Table { 18, 1000000000000000000UL },
String_Length_Table { 19, UINT64_MAX },
String_Length_Table { 19, UINT64_MAX },
String_Length_Table { 19, UINT64_MAX },
String_Length_Table { 19, 10000000000000000000UL },
};
void print_internal_uint64_t(uint64_t v) {
Print_Buffer output = {0};
uint64_t table_index = 64 - __builtin_clzll(v);
String_Length_Table entry = string_length_table[table_index];
uint32_t string_length = entry.length;
if(v >= entry.limit) {
string_length += 1;
}
size_t i = 0;
while(true) {
i += 1;
output.view_8[string_length - i] = (v % 10) + '0';
v /= 10;
if(v == 0) {
break;
}
}
printf("%s\n", output.view_8);
}
void print_n(uint64_t v) {
printf("uint64_t: ");
print_internal_uint64_t(v);
}
void print_n(int64_t v) {
printf("int64_t: ");
if(v < 0) {
printf("-");
v = -v;
}
print_internal_uint64_t(v);
}
uint64_t pow10(uint64_t count) {
uint64_t result = 1;
for(size_t i = 0; i < count; ++i) {
result *= 10;
}
return result;
}
int main() {
for(size_t i = 0; i < 64; ++i) {
#if 0
//printf("%.2zu ", i);
uint32_t length_small = 0;
print_internal_uint64_t(1UL << i, &length_small);
printf("|");
//printf("%.2zu ", i);
uint32_t length_large = 0;
print_internal_uint64_t((1UL << i << 1) - 1, &length_large);
printf("\n");
uint64_t limit = 0;
if(length_small != length_large) {
limit = pow10(length_large - 1);
}
//printf("\tString_Length_Table { %u, %lu },\n", length_small, limit);
//printf("-- %i\n", (int)(i * 0.3 + 1.3));
#endif
print_internal_uint64_t(1UL << i);
print_internal_uint64_t((1UL << i << 1) - 1);
}
printf("--\n");
print_n(UINT64_MAX);
print_n(18446744073709551);
print_n(0UL);
print_n(1UL);
print_n(9UL);
print_n(50UL);
print_n(62UL);
print_n(73L);
print_n(-84L);
print_n(99999999L);
print_n(45645656L);
print_n(35123123123L);
print_n(4564565645645656L);
print_n(99L);
print_n(100L);
return 0;
}