Cod sursa(job #3128620)

Utilizator ecaterinaEcaterina Stefanescu ecaterina Data 10 mai 2023 09:40:54
Problema Potrivirea sirurilor Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.08 kb
#include <iostream>
#include <stdio.h>

#define NMAX 2000001
#define HASHBASE1 256
#define HASHSIZE1 4999999
#define HASHBASE2 256
#define HASHSIZE2 666013

char str[NMAX];
int nstr;
char pat[NMAX];
int npat;
int ap[NMAX];

long long int phash1, phash2, shash1, shash2;

using namespace std;

int main() {
    FILE *fin, *fout;
    fin = fopen("strmatch.in", "r");
    fout = fopen("strmatch.out", "w");
    
    long long int pow1, pow2;
    int i, nrap;
    char ch;
    
    npat = 0;
    ch = fgetc(fin);
    while (ch!='\n' && ch!=' ' && ch!='\r') {
        pat[npat] = ch;
        npat++;
        ch = fgetc(fin);
    }
    nstr = 0;
    while (ch=='\n' || ch==' ' || ch=='\r') {
        ch = fgetc(fin);
    }
    while (ch!='\n' && ch!=' ' && ch!='\r' && ch!=EOF) {
        str[nstr] = ch;
        nstr++;
        ch = fgetc(fin);
    }
    
    pow1 = pow2 = 1;
    for (i=0; i<npat-1; i++) {
        pow1 = (pow1*HASHBASE1)%HASHSIZE1;
        pow2 = (pow2*HASHBASE1)%HASHSIZE2;
    }
    
    for (i=0; i<npat; i++) {
        phash1 = (phash1*HASHBASE1 + pat[i])%HASHSIZE1;
        phash2 = (phash2*HASHBASE2 + pat[i])%HASHSIZE2;
        shash1 = (shash1*HASHBASE1 + str[i])%HASHSIZE1;
        shash2 = (shash2*HASHBASE2 + str[i])%HASHSIZE2;
    }
    
    nrap = 0;
    for (i=npat; i<nstr; i++) {
        if (phash1==shash1 && phash2==shash2) {
            ap[nrap] = i-npat;
            nrap++;
        }
        
        ///remove
        shash1 = (shash1-str[i-npat]*pow1)%HASHSIZE1;
        if (shash1<0) {
            shash1+=HASHSIZE1;
        }
        shash2 = (shash2-str[i-npat]*pow2)%HASHSIZE2;
        if (shash2<0) {
            shash2+=HASHSIZE2;
        }
        
        ///add
        shash1 = (shash1*HASHBASE1 + str[i])%HASHSIZE1;
        shash2 = (shash2*HASHBASE2 + str[i])%HASHSIZE2;
    }
    if (phash1==shash1 && phash2==shash2) {
        ap[nrap] = i-npat;
        nrap++;
    }
    
    fprintf(fout, "%d\n", nrap);
    if (nrap>1000) {
        nrap=1000;
    }
    for (i=0; i<nrap; i++) {
        fprintf(fout, "%d ", ap[i]);
    }
    
    fclose(fin);
    fclose(fout);
    return 0;
}