Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <stdlib.h>
- #include <ctype.h>
- enum
- {
- BIN_SIZE = 32,
- LONG_SIZE = 8
- };
- int
- *get_num(FILE *f)
- {
- unsigned int n = 8;
- unsigned int real_n = 0;
- int *buf, *new_buf;
- int c = fgetc(f);
- buf = NULL;
- while(isspace(c)) {
- c = fgetc(f);
- }
- while(c != EOF && !isspace(c)) {
- if (!buf || real_n + 1 >= n) {
- n <<= 1;
- new_buf = realloc(buf, n * sizeof(*buf));
- if (!new_buf) {
- if (!buf) {
- free(buf);
- }
- return NULL;
- }
- buf = new_buf;
- }
- buf[real_n++] = c - '0';
- c = fgetc(f);
- }
- if (buf) {
- buf[real_n] = -1;
- }
- return buf;
- }
- int
- get_count(int *num)
- {
- int n = 0;
- while (num[n] != -1) {
- n++;
- }
- return n;
- }
- void
- rev(int *s, int n)
- {
- int c;
- for (int i = 0; i < n / 2; i++) {
- c = s[i];
- s[i] = s[n - i - 1];
- s[n - i - 1] = c;
- }
- }
- int
- mult2_dec(int *num, int n, int *first)
- {
- int not_null = 0;
- int v = 0;
- if (*first == n) {
- return -1;
- }
- for (int i = *first; i < n; i++) {
- if (num[i] && !not_null) {
- not_null = 1;
- *first = i;
- }
- num[i] *= 2;
- num[i] += v;
- v = num[i] / 10;
- num[i] %= 10;
- if (i + 1 == n) {
- if (not_null) {
- return v;
- }
- *first = n;
- return -1;
- }
- }
- return 0;
- }
- int
- add1_rev_bin(int *num, int n)
- {
- num[n - 1]++;
- for (int i = n - 1; i >= 0; i--) {
- if (num[i] > 1) {
- num[i] = 0;
- if (!i) {
- return 1;
- }
- num[i - 1]++;
- } else {
- return 0;
- }
- }
- return 0;
- }
- char
- *bin_to_hex(int *ans, int n)
- {
- char c;
- char *hex_ans = calloc(n / 4 + 1, sizeof(*hex_ans));
- for (int i = 0; i < n; i += 4) {
- c = ans[i] * 8 + ans[i + 1] * 4 + ans[i + 2] * 2 + ans[i + 3] * 1;
- c += '0';
- if (c > '9') {
- c += ('a' - '0' - 10);
- }
- hex_ans[i / 4] = c;
- }
- return hex_ans;
- }
- int
- *dec_rev_to_bin_32(unsigned long long dec)
- {
- int *bin_ans = calloc(BIN_SIZE, sizeof(*bin_ans));
- for (int i = 0; i < BIN_SIZE; i++) {
- bin_ans[BIN_SIZE - i - 1] = dec % 2;
- dec /= 2;
- }
- return bin_ans;
- }
- void
- print8(char *ans)
- {
- int i = 0;
- while (ans[i]) {
- for (int j = 0; j < 8; j++) {
- fputc(ans[i++], stdout);
- }
- printf(" ");
- }
- printf("\n");
- }
- unsigned long long
- my_pow(int x, int st)
- {
- unsigned long long ans = 1;
- for (int i = 0; i < st; i++) {
- ans *= x;
- }
- return ans;
- }
- int
- my_min(int a, int b)
- {
- return a < b ? a : b;
- }
- unsigned long long
- mult2_32(unsigned long long *num, int n)
- {
- unsigned long long off = 0;
- unsigned long long null_mark = -1;
- for (int i = 0; i < n; i += LONG_SIZE) {
- int k = i / LONG_SIZE;
- if (num[k] != 0) {
- null_mark = 0;
- }
- num[k] <<= BIN_SIZE;
- num[k] += off;
- off = num[k] / my_pow(10, my_min(LONG_SIZE, n - i));
- num[k] %= my_pow(10, my_min(LONG_SIZE, n - i));
- }
- if (null_mark) {
- return null_mark;
- }
- return off;
- }
- int
- main(void)
- {
- int prec;
- fscanf(stdin, "%d", &prec);
- int *num = get_num(stdin);
- int n = get_count(num);
- rev(num, n);
- int c = 0;
- int add_count = (BIN_SIZE - prec % BIN_SIZE) % BIN_SIZE;
- int *ans = calloc(prec + add_count, sizeof(*ans));
- int null_mark = 0;
- int last = 0;
- int first = 0;
- unsigned long long *long_num = calloc((n - 1) / LONG_SIZE + 1, sizeof(*long_num));
- for (int i = 0; i < n; i += LONG_SIZE) {
- for (int j = LONG_SIZE - 1; j >= 0; j--) {
- if (i + j < n) {
- long_num[i / LONG_SIZE] = long_num[i / LONG_SIZE] * 10 + num[i + j];
- }
- }
- }
- unsigned long long off = 0;
- for (int i = 0; i < prec / BIN_SIZE; i++) {
- if (null_mark) {
- break;
- }
- off = mult2_32(long_num, n);
- if (off == -1) {
- null_mark = 1;
- off = 0;
- }
- int *bin_ans = dec_rev_to_bin_32(off);
- for (int j = 0; j < BIN_SIZE; j++) {
- ans[i * BIN_SIZE + j] = bin_ans[j];
- }
- free(bin_ans);
- last = i + 1;
- }
- if (!null_mark) {
- for (int i = 0; i < n; i += LONG_SIZE) {
- for (int j = 0; j < LONG_SIZE; j++) {
- if (i + j < n) {
- num[i + j] = long_num[i / LONG_SIZE] % 10;
- long_num[i / LONG_SIZE] /= 10;
- }
- }
- }
- }
- for (int i = last * BIN_SIZE; i < prec; i++) {
- if (null_mark) {
- ans[i] = 0;
- } else {
- ans[i] = mult2_dec(num, n, &first);
- if (ans[i] == -1) {
- ans[i] = 0;
- null_mark = 1;
- }
- }
- }
- if (!null_mark) {
- if (mult2_dec(num, n, &first) == 1 && (ans[prec - 1] == 1 || mult2_dec(num, n, &first) != -1)) {
- c = add1_rev_bin(ans, prec);
- }
- if (c) {
- printf("1 ");
- }
- }
- prec += add_count;
- char *hex_ans = bin_to_hex(ans, prec);
- print8(hex_ans);
- free(ans);
- free(hex_ans);
- free(num);
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement