#include <iostream> using namespace std; typedef long long int ll; #define MOD 1000000007 char cc[302][302]; int tt[302][302]; int dr[8][2]={{-1,-1},{-1,1},{1,1},{1,-1},{0,1},{0,-1},{1,0},{-1,0}}; inline int getNum(int j,int k,int N){ int cnt=0; for(int i=0;i<8;i++){ int x=j+dr[i][0],y=k+dr[i][1]; if(x>=0&&x<N&&y>=0&&y<N) cnt+=cc[x][y]=='*'?1:0; } return cnt; } void dfs(int j,int k,int N){ int tmp=tt[j][k]; tt[j][k]=-1; if(tmp!=0) return; for(int i=0;i<8;i++){ int x=j+dr[i][0],y=k+dr[i][1]; if(x>=0&&x<N&&y>=0&&y<N){ dfs(x,y,N); } } } int main(){ int n;cin>>n; for(int i=1;i<=n;i++){ int N;cin>>N; for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ char c;cin>>c; cc[j][k]=c; } } for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ // *=-2, char c=cc[j][k]; tt[j][k]=c=='*'?-2:getNum(j,k,N); } } /* for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ cout<<tt[j][k]<<" "; }cout<<endl; } */ int cnt=0; for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ if(tt[j][k]==0){ cnt++; dfs(j,k,N); } } } /* for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ cout<<tt[j][k]<<" "; }cout<<endl; } */ for(int j=0;j<N;j++){ for(int k=0;k<N;k++){ if(tt[j][k]!=-1&&tt[j][k]!=-2){ cnt++; } } } cout<<"Case #"<<i<<": "<<cnt<<endl; } return 0; }
注意起点车站,可以换乘换到别的路线上的车站。
但是没A,不知道为什么。。。
#include<cstdio> #include <assert.h> #include<cstring> #include<cmath> #include <vector> #include <iostream> using namespace std; int time_[1001][1001]; int d[1001][1001]; int wait[1001]; int start[1001]; void floyd(int n){ for(int j=0;j<n;j++){ for(int k=0;k<n;k++){ d[j][k]=time_[j][k]; } } for(int i=0;i<n;i++){ for(int j=0;j<n;j++){ for(int k=0;k<n;k++){ if(d[j][i]>=0&&d[i][k]>=0){ if(d[j][k]<0||d[j][k]>d[j][i]+d[i][k]) d[j][k]=d[j][i]+d[i][k]; } } } } } int dkl(int time_[][1001],int l,int r,int n){ bool visit[1001]; int d[1001]; memset(d,-1,sizeof(d)); memset(visit,0,sizeof(visit)); d[l]=0; int s=l; while(s!=r){ visit[s]=true; int minT=99999999,minI=-1; for(int i=0;i<n;i++){ if(!visit[i]){ if(time_[s][i]>=0&&(d[i]<0||d[s]+time_[s][i]<d[i])){ d[i]=d[s]+time_[s][i]; //cout<<"go to "<<i<<" from "<<s<<" with "<<d[s]<<" to "<<d[i]<<endl; } if(d[i]>=0&&d[i]<minT) minI=i,minT=d[i]; } } //if(minI>=0) cout<<"go to "<<minI<<" time_:"<<d[minI]<<endl; s=minI; if(s<0) break; } return d[r]; } int main(){ int casen; cin>>casen; typedef pair<int,int> Pair; for(int casei=1;casei<=casen;casei++){ memset(time_,-1,sizeof(time_)); memset(wait,0,sizeof(wait)); vector<vector<pair<int,int> > >tunes(1001,vector<Pair>()); int N;cin>>N; //cout<<N<<" lines"<<endl; int num=0; for(int i=0;i<N;i++){ int ni,wi; cin>>ni>>wi; wait[i]=wi; assert(wait[i]>=0); //cout<<ni<<" stations, wait: "<<wait[i]<<endl; start[i]=num,num+=ni; for(int j=0;j<ni-1;j++){ int l=start[i]+j,r=start[i]+j+1; int a;cin>>a; //cout<<l<<": "<<r<<"="<<a<<endl; time_[l][r]=time_[r][l]=a; } } int M;cin>>M; //cout<<M<<" tunes"<<endl; for(int i=0;i<M;i++){ int l1,s1,l2,s2,ti; cin>>l1>>s1>>l2>>s2>>ti; l1--,l2--,s1--,s2--; assert(l1!=l2); int l=start[l1]+s1,r=start[l2]+s2; tunes[l].push_back(Pair(r,l2)); tunes[r].push_back(Pair(l,l1)); time_[l][r]=ti+wait[l2]; time_[r][l]=ti+wait[l1]; //cout<<l<<": "<<r<<"="<<time_[l][r]<<" wait[r]:"<<wait[l2]<<endl; } int q;cin>>q; printf("Case #%d:\n",casei); //cout<<q<<" queies"<<endl; floyd(num); for(int i=0;i<q;i++){ int l1,s1,l2,s2; cin>>l1>>s1>>l2>>s2; l1--,l2--,s1--,s2--; int l=start[l1]+s1,r=start[l2]+s2; assert(l!=r); int s=d[l][r]>=0?d[l][r]+wait[l1]:-1; for(int j=0;j<tunes[l].size();j++){ Pair & k=tunes[l][j]; int t=wait[k.second]; cout<<"tune from "<<l<<" to "<<k.first<<endl; if(s<0||d[k.first][r]>=0&&s>t+d[k.first][r]) s=t+d[k.first][r]; } //cout<<l<<":"<<r<<endl; printf("%d\n",s);//+wait[l1]); } } return 0; }
上题答案存在多处问题:
1 没考虑可以沿着隧道从起点走到终点
2 没考虑在隧道里走a->b->c.
上题目,先沿相同线枚举最短路径。然后中转站之间按照wait时间。然后floyd。
#include<cstdio> #include <assert.h> #include<cstring> #include<cmath> #include <vector> #include <iostream> using namespace std; int time_[1001][1001]; // int wait[1001]; int start[1001]; int d[1001][1001]; int lst[1001][1001]; void floyd(int n){ memset( d, -1, sizeof( d )); memset( lst, -1, sizeof( lst )); for( int i = 0; i < n; i++ ) for( int j = 0; j < n; j++ ) d[i][j] = time_[i][j], lst[i][j] = j; for( int i = 0; i < n; i++ ) for( int j = 0; j < n; j++ ) for( int k = 0 ; k < n ; k++ ) if( d[j][i] >= 0 && d[i][k] >= 0 ) if( d[j][k] <0 || d[j][k] > d[j][i] + d[i][k] ) d[j][k] = d[j][i] + d[i][k], lst[j][k] = lst[j][i]; } int dkl(int l,int r,int n){ bool visit[1001]; int d[1001], lst[1001]; memset( d, -1, sizeof( d ) ); memset( lst, -1, sizeof( lst ) ); memset( visit, 0, sizeof( visit ) ); d[l] = 0; int s = l; while(s != r){ visit[s] = true; int minT = 99999999, minI = -1; for( int i = 0; i < n; i ++ ){ if( !visit[i] ){ if( time_[s][i] >= 0 && ( d[i]<0 || d[s] + time_[s][i] < d[i] ) ){ d[i] = d[s] + time_[s][i]; lst[i] = s; } if( d[i] >= 0 && d[i] < minT ) minI = i, minT = d[i]; } } s = minI; if( s < 0 ) break; } /* int i = s; printf( "path from %d to %d : \n", l, r); while( true ){ cout<<i<<" "; i = lst[i]; if( i < 0 ) break; } cout<<endl; cout<<"d[r]:"<<d[r]<<endl; */ return d[r]; } int main(){ int casen; cin >> casen; typedef pair < int, int > Pair; for( int casei = 1; casei <= casen; casei++ ){ memset( time_, -1, sizeof(time_) ); int N; cin >> N; int num=0; // input line stations for( int i = 0 ; i < N ; i++ ){ int ni, wi; cin >> ni >> wi; // wait[i] = wi; start[i] = num, num += ni; for( int j = 0 ; j < ni - 1 ; j++ ){ int l=start[i]+j,r=start[i]+j+1; int a; cin >> a; time_[l][r] = time_[r][l] = a; } for( int j = 0 ; j < ni ; j++ ){ // @error: j < ni - 1, copied from above, is wrong logic for (j,k) enumeration for( int k = j + 2 ; k < ni ; k++ ){// @error: k < ni - 1, copied from above, is wrong logic for (j,k) enumeration int l = start[i] + j, r = start[i] + k; time_[r][l] = time_[l][r] = time_[l][r-1] + time_[r-1][r]; } } for( int j = 0 ; j < ni ; j++ ){ // @error: j < ni - 1, copied from above, is wrong logic for (j,k) enumeration for( int k = j + 1 ; k < ni ; k++ ){// @error: k < ni - 1, copied from above, is wrong logic for (j,k) enumeration // @error: int k = j + 2, copied from above, is wrong logic for (j,k) int l = start[i] + j, r = start[i] + k; time_[r][l] = time_[l][r] = time_[l][r] + wi; } } } // input tune stations int M;cin >> M; for( int i = 0 ;i < M ; i ++ ){ int l1, s1, l2, s2, ti; cin >> l1 >> s1 >> l2 >> s2 >> ti; l1--,l2--,s1--,s2--; assert(l1!=l2); int l = start[l1] + s1, r = start[l2] + s2; assert( l1 != l2 ); time_[l][r] = time_[r][l] = time_[l][r] < 0 ? ti : min( time_[l][r], ti ); } // input queries int q; cin >> q; //// for debug floyd( num ); printf( "Case #%d:\n", casei ); for( int i = 0 ; i < q ; i ++ ){ int l1,s1,l2,s2; cin >>l1>>s1>>l2>>s2; l1--, l2--, s1--, s2--; int l = start[l1] + s1, r = start[l2] + s2; int dst = dkl( l, r, num ); printf( "%d\n", dst ); ////assert( dst == d[l][r] ); } } return 0; }
a[n]=MAXN or min(a[k]+a[n/k]+1,len(n) if n can be input by keyboard).
答案是a[n]+1 or impossible注意如果一个数可以直接用键盘打,就不要用乘法间接算了。
#include<cstdio> #include<cstring> #include<cmath> using namespace std; int a[1000005],b[10]; int check( int x ) { int ans = 0; while ( x != 0 ) { if ( b[x%10] == 0 ) return 0; ans++; x = x / 10; } return ans; } int main() { int cas; int c = 0; scanf( "%d", &cas ); while ( cas-- ) { for ( int i = 0; i <= 1000000; i++ ) a[i] = 0; int n; for ( int i = 0; i < 10; i++ ) b[i] = 0; for ( int i = 0; i < 10; i++ ) { scanf( "%d", &n ); if ( n == 1 ) a[i] = 1; if ( n == 1 ) b[i] = 1; } scanf( "%d", &n ); for ( int i = 2; i <= n; i++ ) { if ( a[i] != 0 ) continue; a[i] = check(i); int p = int(sqrt(i)); for ( int j = 2; j <= p; j++ ) if ( (i % j) == 0 && a[j] != 0 && a[i/j] != 0 ) { if ( a[i] == 0 ) a[i] = a[j] + a[i/j] + 1; else if ( a[i] > a[j] + a[i/j] + 1 ) a[i] = a[j] + a[i/j] + 1; } } c++; printf("Case #%d: ",c); if ( a[n] != 0 ) printf("%d\n",a[n]+1); else printf("Impossible\n"); } return 0; }
#include<iostream> #include<bitset> using namespace std; int matrix[104][104]; int sum[104]; int W; int H; int N; int t; int r; int tet_x; int flag = 1; int tet[8][4]; int line[8][4]; void init(){ tet[1][0] = 0x8c4; line[1][0] = 3; tet[1][1] = 0x6c; line[1][1] = 2; tet[1][2] = 0x8c4; line[1][2] = 3; tet[1][3] = 0x6c; line[1][3] = 2; tet[2][0] = 0x4c8; line[2][0] = 3; tet[2][1] = 0xc6; line[2][1] = 2; tet[2][2] = 0x4c8; line[2][2] = 3; tet[2][3] = 0xc6; line[2][3] = 2; tet[3][0] = 0x88c; line[3][0] = 3; tet[3][1] = 0x2e; line[3][1] = 2; tet[3][2] = 0xc44; line[3][2] = 3; tet[3][3] = 0xe8; line[3][3] = 2; tet[4][0] = 0x44c; line[4][0] = 3; tet[4][1] = 0xe2; line[4][1] = 2; tet[4][2] = 0xc88; line[4][2] = 3; tet[4][3] = 0x8e; line[4][3] = 2; tet[5][0] = 0xcc; line[5][0] = 2; tet[5][1] = 0xcc; line[5][1] = 2; tet[5][2] = 0xcc; line[5][2] = 2; tet[5][3] = 0xcc; line[5][3] = 2; tet[6][0] = 0x8888; line[6][0] = 4; tet[6][1] = 0xf; line[6][1] = 1; tet[6][2] = 0x8888; line[6][2] = 4; tet[6][3] = 0xf; line[6][3] = 1; tet[7][0] = 0x4e; tet[7][1] = 0x4c4; tet[7][2] = 0xe4; tet[7][3] = 0x8c8; int a=42486; bitset<32> bs(a); /* for(int i = 1; i<8;i++){ for(int j = 0;j<4;j++){ cout<<"here is the tet "<<i<<" "<<j<<endl; bitset<32> bs(tet[i][j]); cout<<bs<<endl; for(int i = 3;i>=0;i--){ cout<<bs[4*i+3]<<bs[4*i+2]<<bs[4*i+1]<<bs[4*i]<<endl; } } } */ } void printMatrix(){ if(flag == 1){ for(int i = H-1;i>=0;i--){ for(int j=0; j<W;j++){ if(matrix[i][j] == 1){ cout<<"x"; }else{ cout<<"."; } } // cout<<" sum is: "<<sum[i]<<endl; cout<<endl; } }else{ cout<<"Game Over!"<<endl; } } void moveMatrix(int y){ int index = 0; for(int i = y; i<H; i++){ if(sum[i] == W){ index ++; for(int j = i+1;j<H;j++){ if(sum[j] == W) index ++; } } if(index != 0){ for(int j = 0;j<W;j++){ matrix[i][j] = matrix[i+index][j]; } sum[i] = sum[i+index]; } } } void putTet(int y,int x,int right){ if(right == 0){ return; } for(int i=0;i<4;i++){ int a = 1<<i; int notZero = (right & a)>>i; // cout<<"here a is: "<<a<<"here notZero is: "<<notZero<<endl; if(notZero == 1){ matrix[y][x+3-i] = notZero; sum[y]++; // if(sum[y]>W){ // printMatrix(); // system("pause"); // } // cout<<"here y is: "<<y<<" "<<"here sum is:"<<sum[y]<<endl; // for(int i = 0;i<H;i++){ // // for(int j =0; j<W;j++){ // cout<<matrix[i][j]<<" "; // } // cout<<endl; // } } } } int start(int type , int rotation, int my_x){ int my_tet = tet[type][rotation]; int isStop = 0; int loc_flag = 1; int y; int x; for(y = H-1, x= my_x; y>=0; y--){ isStop = 0; for(int j = 0; j<4; j++){ int temp = (matrix[y+j][x]<<3)|(matrix[y+j][x+1]<<2)|(matrix[y+j][x+2]<<1)|(matrix[y+j][x+3]);//y 能不能放 isStop = isStop|(temp<<j); } isStop = my_tet&isStop; if(isStop !=0 ){ break; } } if(y == H-1){// H loc_flag = 0; }else{ y++; int right[4]; right[0] = (my_tet&0x000f); right[1] = (my_tet&0x00f0)>>4; right[2] = (my_tet&0x0f00)>>8; right[3] = (my_tet&0xf000)>>12; for(int i=0;i<4;i++){ /* if(y+i>=H && right[i]!=0){ loc_flag = 0; break; } */ // cout<<"here right is: "<<right[i]<<endl; putTet(y+i,my_x,right[i]); } moveMatrix(y); for(int i=H;i<H+4;i++){ if(sum[i]!=0) { loc_flag=0; break; } } } return loc_flag; } int main(){ int T; init(); cin >>T; for(int i=0;i<T;i++){ cin >> W >>H >>N; flag = 1; for(int i = 0;i<H+4;i++){ for(int j = 0;j<W+4;j++){ matrix [i][j] = 0; } sum [i] = 0; } for(int i=0;i<N;i++){ cin>>t>>r>>tet_x; if(flag == 1){ flag = start(t,r,tet_x); }else{ continue; } // printMatrix(); } cout<<"Case #"<<i+1<<":"<<endl; printMatrix(); } // cout<<endl<<"end"<<endl; // cout<<"dadad: "<<sum[0]<<endl; // system("pause"); return 1; }