现在的位置: 首页 > 综合 > 正文

【google apec 2015 1c】 挖矿、打地铁 最短路djstra、+*计算器

2018年04月12日 ⁄ 综合 ⁄ 共 10010字 ⁄ 字号 评论关闭

Problem A. Minesweeper  

http://code.google.com/codejam/contest/5214486/dashboard#s=p0

Problem B. Taking
Metro

http://code.google.com/codejam/contest/5214486/dashboard#s=p1

Problem
C.
 Broken Calculator

http://code.google.com/codejam/contest/5214486/dashboard#s=p2

Problem
D.
 Tetris

http://code.google.com/codejam/contest/5214486/dashboard#s=p3

第一题:贪心法,先消除0

#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;
}

第二题:最短路径(dilijstra、floyd?) 

注意起点车站,可以换乘换到别的路线上的车站。

但是没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;
}

第三题:dp。

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;
}

第四题 为什么a不了?

#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;             
}

抱歉!评论已关闭.