队列。help
士兵队列
--------------------------------------------
Time limit: 1000MS Memory limit: 32768K
Total Submit: 248 Accepted: 106
--------------------------------------------
国王刚刚打了一场胜仗,但有很多士兵牺牲了,所以原来的的矩阵队列有很多的空位。因此国王将士兵重新排列,他要求士兵按照原来的列的大小来排列,有空位的要补齐。
补齐的方式如下:
(1) 同一行,前面有空位的后面士兵补齐,如果该行士兵没补满,下面一行的补上。
(2) 递归重复步骤(1)直到士兵之间没有空位。
排好后国王才想到,这样排的话,把原来位置上士兵的战斗值搞混了,然而他又没有备份,如果撤销排队命令的话,又显得没有威信,所以一时有点郁闷了,你能帮他解决这个问题吗?
输入:
有多组测试数据。
原来队列的行列数n,m(1 <= n, m <= 1000)。接着是原来的队列,非0数表示这个位置上士兵的战斗值,0表示这个位置的士兵已经牺牲。然后一个数k,下面k行中每一行包含2个整数x, y (1 <= x <= n, 1 <= y <= m), 表示排列前这个士兵的位置。
输出:
对于每个位置,输出重新排列后,该士兵的位置。
Sample Input:
3 3
5 0 3
4 5 0
6 5 0
2
1 1
2 1
Sample Output:
1 1
1 3
我的代码超时了。实在无路可走了。没学过多少算法,请好心人帮忙。
我的代码:
#include<iostream>
#include<cstring>
using namespace std;
struct sold
{
int power;
}sold[1010][1010];
int main()
{
int Row,Line,N,testR,testL;
int i,j,sum,row,line;
while(cin>>Line>>Row)
{
for(i=1;i<=Line;i++)
{
for(j=1;j<=Row;j++)
{
cin>>sold[i][j].power;
}
}
cin>>N;
while(N--)
{
sum=0;
cin>>testL>>testR;
line=testL;
row=testR;
for(i=1;i<testL;i++)
for(j=1;j<=Row;j++)
{
if(sold[i][j].power==0)
sum++;
}
while(sum--)
{
row--;
if(row==0)
{
row=Row;
line--;
}
}
for(j=1;j<testR;j++)
{
if(sold[i][j].power==0)
{
row--;
if(row==0)
{
row=Row;
line--;
}
}
}
cout<<line<<" "<<row<<endl;
}
}
return 0;
}
[解决办法]
简单的模拟。。按他的要求做就是了。 。
但是一开始没考虑到n<=3的情况导致错了两次。。
下面是AC代码:
#include<iostream>using namespace std;int f[5009];int main(){ int t; int n,i; while(cin>>t) { while(t--) { cin>>n; for(i=1;i<=n;i++) f[i]=i; int t; if(n<=3) { printf("1"); for(i=2;i<=n;i++) printf(" %d",i); printf("\n"); continue; } while(1) { int leap=0; for(i=1;i<=n;i++) { if(f[i]!=-1) { leap++; } if(leap==2) { leap=0; f[i]=-1; } } t=0; for(i=1;i<=n;i++) if(f[i]!=-1) t++; if(t<=3) break; leap=0; for(i=1;i<=n;i++) { if(f[i]!=-1) leap++; if(leap==3) { f[i]=-1; leap=0; } } t=0; for(i=1;i<=n;i++) if(f[i]!=-1) t++; if(t<=3) break; } for(i=1;i<=n;i++) if(f[i]!=-1) { printf("%d",f[i]); break; } i++; for(;i<=n;i++) if(f[i]!=-1) printf(" %d",f[i]); printf("\n"); } } return 0;}