下面有非常高效的代码。这题给出的A……ZZZ共18278列是纸老虎,这只老虎很吓人,老是诱惑人走进超时的怪圈。实则开一个1001*1001的数组就足矣。两个方法,一个是用简单的topo排序一下。另外一个是,链表处理。如D1这个格子,D1=A1+B1+C1。那么在A1,B1,C1三个单元格的出度指向域中保存D1,便可从A1,B1,C1出发,搜索到D1,便把当前的单元格值加到D1的单元格值上,G[p->x][p->y].v+=G[x][y].v;
一:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<ctype.h>
const int maxn=1001*1001;
int in[maxn],G[maxn][100],c,r,sheet[maxn];
bool dfs(int u)
{
int s=0;
for(int i=0; i<in[u]; i++)
{
if(in[G[u][i]] && !dfs(G[u][i])) return false;
s+=sheet[G[u][i]];
}
sheet[u]=s;
in[u]=0;
return true;
}
bool toposort()
{
for(int i=0; i<r*c; i++)
if(in[i] &&!dfs(i)) return false;
return true;
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("196.txt","r",stdin);
#endif
int t,i;
scanf("%d",&t);
while(t--)
{
memset(in,0,sizeof(in));
memset(G,0,sizeof(G));
scanf("%d%d",&c,&r);
for(i=0; i<c*r; i++)
{
char s[1000];
scanf("%s",s);
int k=1,t=0,num=0;
if(s[0]=='=')
{
int len=strlen(s);
s[len]='+';
s[len+1]='\0';
while(s[k])
{
if(isalpha(s[k])) t=t*26+s[k]-'A'+1;
else if(isdigit(s[k])) num=num*10+s[k]-'0';
else
{
G[i][in[i]++]=(num-1)*c+t-1;
num=t=0;
}
k++;
}
}
else sscanf(s,"%d",&sheet[i]);
}
toposort();
for(i=0; i<c*r; i++)
{
if(i && !(i%c)) printf("\n");
if(i%c) printf(" ");
printf("%d",sheet[i]);
}
printf("\n");
}
return 0;
}
二(动态空间):
#include<cstdio>
#include<string.h>
#include<stdlib.h>
#include<ctype.h>
#include<algorithm>
using namespace std;
const int maxn=200;
struct Sheet
{
int x,y,v,in;
Sheet *next;
};
Sheet **G;
int **q,c,r;
char s[200];
void init()
{
G=new Sheet *[r+1];
int i;
for(i=0;i<=r;i++)
G[i]=new Sheet [c+1];
q=new int *[c*r+10];
for(i=0;i<c*r+10;i++)
q[i]=new int [2];
}
void bfs()
{
int i,j,front=0,rear=0;
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
if(!G[i][j].in)
{
q[rear][0]=i;
q[rear++][1]=j;
}
while(front<rear)
{
int x=q[front][0],y=q[front][1];
front++;
//printf("x=%d y=%d\n",x,y);
Sheet *p=G[x][y].next;
while(p)
{
G[p->x][p->y].v+=G[x][y].v;
G[p->x][p->y].in--;
if(!G[p->x][p->y].in)
{
q[rear][0]=p->x;
q[rear++][1]=p->y;
}
p=p->next;
}
}
}
void remove_next(Sheet *p)
{
if(p==NULL) return;
remove_next(p->next);
delete p;
}
void del()
{
int i,j;
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
{
remove_next(G[i][j].next);
}
for(i=0;i<=r;i++)
delete[] G[i];
delete[] G;
for(i=0;i<c*r+10;i++)
delete[] q[i];
delete q;
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("196.txt","r",stdin);
#endif
int t;
scanf("%d",&t);
while(t--)
{
scanf("%d%d\n",&c,&r);
init();
//G[r][c].v=10;
//printf("%d\n",G[r][c].v);
//q[c*r-1][0]=10;
//printf("%d\n",q[c*r-1][0]);
int i,j;
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
{
G[i][j].x=G[i][j].y=G[i][j].v=G[i][j].in=0;
G[i][j].next=NULL;
}
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
{
scanf("%s",s);
if(s[0]!='=')
sscanf(s,"%d",&G[i][j].v);
else
{
int letter=0,num=0;
int len=strlen(s);
s[len]='+';
s[len+1]='\0';
for(int k=1;s[k]!='\0';k++)
{
if(isalpha(s[k])) letter=letter*26+s[k]-'A'+1;
else if(isdigit(s[k])) num=num*10+s[k]-'0';
else
{
//Sheet *p=(Sheet *)malloc(sizeof(Sheet));
Sheet *p=new Sheet;
p->in=p->v=0;
p->x=i;
p->y=j;
G[i][j].in++;
p->next=G[num][letter].next;
G[num][letter].next=p;
num=letter=0;
}
}
}
}
/*for(int i=1;i<=r;i++,printf("\n"))
for(int j=1;j<=c;j++)
{
if(G[i][j].in) printf("no ");
else printf("%d ",G[i][j].v);
}*/
bfs();
for(i=1;i<=r;i++,printf("\n"))
for(j=1;j<=c;j++)
{
if(j>1) printf(" ");
printf("%d",G[i][j].v);
}
del();
}
return 0;
}
二(静态空间,最快):
#include<cstdio>
#include<string.h>
#include<stdlib.h>
#include<ctype.h>
#include<algorithm>
using namespace std;
const int maxn=1001;
struct Sheet
{
int x,y,v,in;
Sheet *next;
};
Sheet G[maxn][maxn];
int q[maxn*maxn][2],c,r;
char s[200];
void bfs()
{
int i,j,front=0,rear=0;
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
if(!G[i][j].in)
{
q[rear][0]=i;
q[rear++][1]=j;
}
while(front<rear)
{
int &x=q[front][0],&y=q[front][1];
front++;
//printf("x=%d y=%d\n",x,y);
Sheet *p=G[x][y].next;
while(p)
{
G[p->x][p->y].v+=G[x][y].v;
G[p->x][p->y].in--;
if(!G[p->x][p->y].in)
{
q[rear][0]=p->x;
q[rear++][1]=p->y;
}
p=p->next;
}
}
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("196.txt","r",stdin);
#endif
int t;
scanf("%d",&t);
while(t--)
{
scanf("%d%d\n",&c,&r);
//G[r][c].v=10;
//printf("%d\n",G[r][c].v);
//q[c*r-1][0]=10;
//printf("%d\n",q[c*r-1][0]);
int i,j;
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
{
G[i][j].x=G[i][j].y=G[i][j].v=G[i][j].in=0;
G[i][j].next=NULL;
}
for(i=1;i<=r;i++)
for(j=1;j<=c;j++)
{
scanf("%s",s);
if(s[0]!='=')
sscanf(s,"%d",&G[i][j].v);
else
{
int letter=0,num=0;
int len=strlen(s);
s[len]='+';
s[len+1]='\0';
for(int k=1;s[k]!='\0';k++)
{
if(isalpha(s[k])) letter=letter*26+s[k]-'A'+1;
else if(isdigit(s[k])) num=num*10+s[k]-'0';
else
{
//Sheet *p=(Sheet *)malloc(sizeof(Sheet));
Sheet *p=new Sheet;
p->in=p->v=0;
p->x=i;
p->y=j;
G[i][j].in++;
p->next=G[num][letter].next;
G[num][letter].next=p;
num=letter=0;
}
}
}
}
/*for(int i=1;i<=r;i++,printf("\n"))
for(int j=1;j<=c;j++)
{
if(G[i][j].in) printf("no ");
else printf("%d ",G[i][j].v);
}*/
bfs();
for(i=1;i<=r;i++,printf("\n"))
for(j=1;j<=c;j++)
{
if(j>1) printf(" ");
printf("%d",G[i][j].v);
}
}
return 0;
}