Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- # include <stdlib.h>
- # include <unistd.h>
- # include <fcntl.h>
- typedef unsigned long t_bitset;
- unsigned long g_len;
- t_bitset *init_first_line(int fd);
- t_bitset *init_bitset(int fd, int line);
- t_bitset *init_bitset_from_str(char *str);
- char g_f;
- char g_o;
- char g_e;
- int g_n;
- int g_x;
- int g_y;
- int g_numlongs;
- int g_search_size;
- char *g_str;
- char g_first[13];
- t_bitset *g_map;
- void solve(t_bitset **map);
- int store_map(t_bitset ***map, char *file);
- void check_existence(int existence, t_bitset **map);
- void set_globals(char *str, int i);t_bitset *bs_copy(t_bitset *set);
- void bs_and(t_bitset *set1, t_bitset *set2);
- void bs_shift(unsigned long **bits);
- int existence(t_bitset *set, int line);
- void ft_putchar(char c, int fd);
- int print_error(void);
- int check_error(t_bitset **map);
- void add_full_chars(void);
- void input(t_bitset ***map);
- int ft_atoi(char *str);
- char *str_realloc_double(char *str, unsigned long buff);
- char *str_realloc(char **str, unsigned long buff);
- int g_i;
- int g_l;
- int g_k;
- void bs_and(t_bitset *set1, t_bitset *set2)
- {
- int i;
- i = 0;
- while (i < g_numlongs)
- {
- set1[i] &= set2[i];
- i++;
- }
- }
- t_bitset *bs_copy(t_bitset *set)
- {
- t_bitset *output;
- int i;
- output = (t_bitset *)malloc(sizeof(unsigned long) * g_numlongs);
- i = 0;
- while (i < g_numlongs)
- {
- output[i] = set[i];
- i++;
- }
- return (output);
- }
- void bs_shift(unsigned long **bits)
- {
- int i;
- i = 0;
- while (i < g_numlongs - 1)
- {
- (*bits)[i] &= ((*bits)[i] << 1) | (((*bits)[i + 1] >> 63) & 1);
- ++i;
- }
- (*bits)[g_numlongs - 1] &= (*bits)[g_numlongs - 1] << 1;
- }
- int existence(t_bitset *set, int line)
- {
- int i;
- int j;
- unsigned long b;
- i = 0;
- b = 0;
- while (i < g_numlongs && !b)
- b = (set[i++]);
- j = 0;
- while (b && j < 64)
- {
- if (b & (((unsigned long)1 << 63) >> j))
- {
- g_x = (i - 1) * 64 + j;
- g_y = line;
- return (1);
- }
- ++j;
- }
- return (0);
- }
- void solve(t_bitset **map)
- {
- int s;
- g_i = 0;
- g_l = 0;
- g_k = 0;
- g_search_size = 1;
- while (g_i + g_search_size <= g_n)
- {
- while (g_l < g_search_size - 1)
- bs_shift(&(map[g_i + g_l++]));
- while (g_k < g_search_size - 1)
- {
- bs_shift(&(map[g_i + g_search_size - 1]));
- g_k++;
- }
- s = 1;
- while (s < g_search_size)
- bs_and(map[g_i], map[g_i + s++]);
- check_existence(existence(map[g_i], g_i), map);
- }
- }
- void check_existence(int existence, t_bitset **map)
- {
- int p;
- if (existence)
- {
- g_l = 0;
- g_k = 0;
- ++g_search_size;
- }
- else
- {
- ++g_i;
- p = 0;
- while (g_i + g_search_size <= g_n && p < g_search_size - 1)
- {
- if (g_i + g_search_size <= g_n)
- bs_shift(&(map[g_i + g_search_size - 1]));
- p++;
- }
- }
- }
- t_bitset *init_first_line(int fd)
- {
- unsigned int i;
- unsigned int buff;
- buff = 16;
- g_str = (char *)malloc(sizeof(char) * buff);
- i = 0;
- while (read(fd, &g_str[i], 1) && g_str[i] ^ '\n')
- {
- if (i + 1 == buff)
- {
- buff <<= 1;
- g_str = str_realloc_double(g_str, buff);
- }
- i++;
- }
- g_numlongs = i / 64 + (i % 64 != 0);
- g_len = i;
- if (g_len == 0)
- return ((void *)0);
- return (init_bitset_from_str(g_str));
- }
- t_bitset *init_bitset_from_str(char *str)
- {
- t_bitset *output;
- unsigned int i;
- output = (t_bitset *)malloc(sizeof(t_bitset) * g_numlongs);
- i = -1;
- while (++i < (unsigned int)g_numlongs)
- output[i] = 0;
- i = 0;
- while (i < g_len)
- {
- if (str[i] != g_e && str[i] != g_o)
- return ((void *)0);
- output[i / 64] |= (((unsigned long)(str[i] == g_e) << 63) >> (i % 64));
- i++;
- }
- return (output);
- }
- t_bitset *init_bitset(int fd, int line)
- {
- int ret;
- ret = read(fd, &(g_str[line]), g_len + 1);
- if (ret > 0)
- {
- return (init_bitset_from_str(&(g_str[line])));
- }
- return ((void *)0);
- }
- void set_globals(char *str, int i)
- {
- int digits;
- int n;
- if (i > 3)
- {
- g_f = str[i - 1];
- g_o = str[i - 2];
- g_e = str[i - 3];
- str[i - 3] = '\0';
- g_n = ft_atoi(str);
- digits = 1;
- n = g_n;
- if (n < 0)
- n *= -1;
- while (n >= 10)
- {
- n /= 10;
- ++digits;
- }
- if (digits + 3 != i || g_o == g_e || g_o == g_f || g_f == g_e)
- g_n = 0;
- }
- }
- int store_map(t_bitset ***map, char *file)
- {
- int i;
- char c;
- int fd;
- fd = open(file, O_RDONLY);
- if (fd < 0)
- return (0);
- i = 0;
- while (read(fd, &c, 1) && c != '\n' && i < 13)
- g_first[i++] = c;
- set_globals(g_first, i);
- (*map) = (t_bitset **)malloc(sizeof(t_bitset *) * g_n);
- (*map)[0] = init_first_line(fd);
- g_str = str_realloc(&g_str, (g_len + 1) * g_n);
- if ((*map)[0] && g_len > 0)
- {
- i = 0;
- while (++i < g_n)
- (*map)[i] = init_bitset(fd, (g_len + 1) * i);
- }
- if (g_str[(g_len + 1) * i - 1] != '\n')
- return (0);
- close(fd);
- return (check_error(*map));
- }
- int print_error(void)
- {
- write(2, "map error\n", 10);
- return (1);
- }
- int check_error(t_bitset **map)
- {
- int i;
- i = 0;
- while (i < g_n)
- {
- if (map[i] == NULL)
- return (0);
- ++i;
- }
- return (g_n);
- }
- void add_full_chars(void)
- {
- int i;
- int j;
- i = g_y;
- while (i < g_y + g_search_size - 1)
- {
- j = g_x;
- while (j < g_x + g_search_size - 1)
- {
- g_str[(g_len + 1) * i + j] = g_f;
- j++;
- }
- i++;
- }
- }
- void input(t_bitset ***map)
- {
- int i;
- i = 0;
- while (read(0, &g_first[i], 1) && g_first[i] != '\n')
- ++i;
- set_globals(g_first, i);
- (*map) = (t_bitset **)malloc(sizeof(t_bitset *) * g_n);
- (*map)[0] = init_first_line(0);
- g_str = str_realloc(&g_str, (g_len + 1) * g_n);
- if ((*map)[0] && g_len > 0)
- {
- i = 0;
- while (++i < g_n)
- (*map)[i] =
- init_bitset(0, (g_len + 1) * i);
- }
- if (check_error(*map))
- {
- solve(*map);
- add_full_chars();
- write(1, g_str, g_n * (g_len + 1));
- free(g_str);
- }
- else
- print_error();
- }
- void ft_putchar(char c, int fd)
- {
- write(fd, &c, 1);
- }
- int ft_atoi(char *str)
- {
- int value;
- int sign;
- value = 0;
- sign = 1;
- while (*str == '\n' || *str == ' ' || *str == '\t' || *str == '\r' ||
- *str == '\v' || *str == '\f')
- {
- ++str;
- }
- if (*str == '+' || *str == '-')
- {
- if (*str == '-')
- return (0);
- str++;
- }
- while ((*str) >= '0' && (*str) <= '9')
- {
- value *= 10;
- value = (sign ? value + (*str - '0') : value - (*str - '0'));
- str++;
- }
- return (value);
- }
- char *str_realloc(char **str, unsigned long buff)
- {
- char *new_str;
- unsigned int i;
- new_str = (char *)malloc(sizeof(char) * buff);
- i = 0;
- while (i < g_len + 1)
- {
- new_str[i] = (*str)[i];
- ++i;
- }
- free((*str));
- return (new_str);
- }
- char *str_realloc_double(char *str, unsigned long buff)
- {
- char *new_str;
- unsigned int i;
- new_str = (char *)malloc(sizeof(char) * buff);
- buff >>= 1;
- i = 0;
- while (i < buff)
- {
- new_str[i] = (str)[i];
- ++i;
- }
- free((str));
- return (new_str);
- }
- int main(int argc, char *argv[])
- {
- t_bitset **map;
- int i;
- map = (void *)0;
- i = 1;
- if (argc == 1)
- input(&map);
- while (i < argc)
- {
- if (store_map(&map, argv[i]))
- {
- solve(map);
- add_full_chars();
- write(1, g_str, g_n * (g_len + 1));
- free(g_str);
- }
- else
- print_error();
- ++i;
- if (argc > 2)
- ft_putchar('\n', 1);
- }
- return (0);
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement