Cod sursa(job #1499736)

Utilizator stoianmihailStoian Mihail stoianmihail Data 11 octombrie 2015 00:38:26
Problema Abc2 Scor 100
Compilator c Status done
Runda Arhiva de probleme Marime 2.01 kb
#include <stdio.h>
#include <string.h>

#define Nadejde 10000005
#define MOD 50001
#define Smerenie 25

#define u32 unsigned int

typedef struct {
  u32 v;
  int next;
} list;

int N, M;
list l[MOD];           // tabela hash.
int adj[MOD];          // capetele resturilor.
int catch, buff;       // variabile necesare.
char s[Smerenie];      // cuvintele din dictionar.
char antique[Nadejde]; // sirul antic.
u32 threes[] = {1, 3, 9, 27, 81, 243, 729, 2187, 6561, 19683, 59049, 177147, 531441, 1594323, 4782969, 14348907, 43046721, 129140163, 387420489, 1162261467, 3486784401};

/** Citeste urmatorul sir din fisier. **/
void read(char *str, int *len, FILE *f) {
  catch = fscanf(f, "%s\n", str);
  (*len) = strlen(str);
}

/** Creeaza functia hash pentru sirul "s". **/
u32 hash() {
  int i;
  u32 h = 0;
  for (i = 0; i < M; i++) {
    h = ((h << 1) + h + s[i] - 'a');
  }
  return h;
}

/** Cauta valoarea "val" in hash. **/
int find(u32 val) {
  int pos = adj[val % MOD];
  while ((pos != 0) && (l[pos].v != val)) {
    pos = l[pos].next;
  }
  return pos;
}

/** Adauga in hash valoarea "val". **/
void add(u32 val) {
  if (!find(val)) {
    int h = val % MOD;
    l[++buff].v = val;
    l[buff].next = adj[h];
    adj[h] = buff;
  }
}

int main(void) {
  FILE *f = fopen("abc2.in", "r");

  /* Citeste sirurile date. */
  read(antique, &N, f);
  read(s, &M, f);
  while (catch != EOF) {
    add(hash());
    read(s, &M, f);
  }
  fclose(f);

  f = fopen("abc2.out", "w");

  u32 h = 0;
  int i = 0, count = 0;

  /* Creeaza functia hash pentru primele M - 1 caractere din sirul antic. **/
  while (i < M - 1) {
    h = ((h << 1) + h + antique[i++] - 'a');
  }
  /* Vezi daca functia curenta se afla in hash. **/
  while (i < N) {
    h = ((h << 1) + h + antique[i] - 'a');
    count += (find(h) > 0);
    h -= (threes[M - 1] * (antique[++i - M] - 'a'));
  }
  fprintf(f, "%d\n", count);
  fclose(f);

  /// Multumim Doamne!
  puts("Doamne ajuta!");
  return 0;
}