Cod sursa(job #1020066)

Utilizator scipianusFMI Ciprian Olariu scipianus Data 1 noiembrie 2013 16:59:05
Problema Diviz Scor 90
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.83 kb
#include<fstream>
#include<cstring>
#include<queue>
#define MOD 30103
using namespace std;
int K,A,B,nrcif,nr[2][210][110],poz[10][210],sol;
char N[210];
struct Stare{
	int last,r;
	Stare(int x,int y)
	{
		last=x;
		r=y;
	}
};
queue <Stare> Q,Q2,sters;
bool bagat[210][110];

int main()
{
	int i,j,lg;
	Stare now = Stare(0,0);
	ifstream fin("diviz.in");
	fin>>K>>A>>B;
	fin>>(N+1); nrcif=strlen(N+1);
	fin.close();
	
	for(i=0;i<10;i++)
		poz[i][nrcif]=nrcif+1;
	for(i=nrcif-1;i>=0;i--)
	{
		for(j=0;j<10;j++)
		{
			if(N[i+1]-'0'==j)
				poz[j][i]=i+1;
			else
				poz[j][i]=poz[j][i+1];
		}
	}
	for(i=1;i<10;i++)
	{
		if(poz[i][0]==nrcif+1)
			continue;
		nr[0][poz[i][0]][i%K]++;
		if(nr[0][poz[i][0]][i%K]==1)
			Q.push(Stare(poz[i][0],i%K));
	}
	lg=1;
	while(lg<=B && !Q.empty())
	{
		while(!Q.empty())
		{
			now=Q.front();
			Q.pop();
			sters.push(now);
			if(lg>=A && now.r==0)
			{
				sol+=nr[0][now.last][now.r];
				if(sol>=MOD)
					sol-=MOD;
			}
			for(i=0;i<10;i++)
			{
				if(poz[i][now.last]!=nrcif+1)
				{
					nr[1][poz[i][now.last]][(now.r*10+i)%K]+=nr[0][now.last][now.r];
					if(nr[1][poz[i][now.last]][(now.r*10+i)%K]>=MOD)
						nr[1][poz[i][now.last]][(now.r*10+i)%K]-=MOD;
					if(!bagat[poz[i][now.last]][(now.r*10+i)%K])
					{
						bagat[poz[i][now.last]][(now.r*10+i)%K]=true;
						Q2.push(Stare(poz[i][now.last],(now.r*10+i)%K));
					}
					
				}
			}
		}
		while(!sters.empty())
		{
			now=sters.front();
			sters.pop();
			nr[0][now.last][now.r]=0;
		}
		while(!Q2.empty())
		{
			now=Q2.front();
			Q2.pop();
			Q.push(now);
			bagat[now.last][now.r]=false;
			nr[0][now.last][now.r]=nr[1][now.last][now.r];
			nr[1][now.last][now.r]=0;
		}
		lg++;
	}
	
	ofstream fout("diviz.out");
	fout<<sol<<"\n";
	fout.close();
	return 0;
}