codeforces 208(div2) A+B+C+D

鏈接:http://codeforces.com/contest/358 

A:

題意:給n個數,按順序的從第一個到最後,從當前點到下一個點,就在兩點之間畫一個弧,問按照順序畫的話,會不會出現有交叉的情況,有則輸出yes否則no

思路:把每一個弧都存下來,判斷當前的弧和之前所有的弧有沒有交叉,O(n^2)的算法。

注意:弧存的時候注意數字大小,判斷弧的時候分情況就行了。

#include<cstdio>
#include<algorithm>
#include<iostream>
#include<string>
#include<cstring>
#include<cmath>
#include<queue>
#include<vector>
using namespace std;
int n;
int a[1005];
struct node{
	int l,r;
}s[1005];
int ind = 0;
int main(){
	cin>>n;
	for (int i = 0; i < n; i++)
	{
		cin>>a[i];
	}
	if(n <= 2)puts("no");
	else{
		int flag = 0;
		int ff = 1;
		int l = a[0],r = a[1];
		if(l > r){ff = 2;}
		s[ind].l = min(l,r);s[ind++].r = max(l,r);
		for (int i = 2; i < n && flag == 0; i++)
		{			
			if(a[i] < r)ff = 2;
			else ff = 1;			
			l = r,r = a[i];
			for (int j = 0; j < ind; j++)
			{
				if(ff == 1){
					if(r > s[j].r && l < s[j].r && l > s[j].l)flag=1;
					else if(l < s[j].l&&r>s[j].l&&r<s[j].r)	flag = 1;
				}else{
					if(l > s[j].r && r < s[j].r && r > s[j].l)flag=1;
					else if(r < s[j].l&&l>s[j].l&&l<s[j].r)	flag = 1;
				}
				if(flag)break;
			}
			s[ind].l = min(l,r);s[ind++].r = max(l,r);
		}
		if(flag)puts("yes");
		else puts("no");
	}
	//system("pause");
	return 0;
}


B:

題意:主角要給女朋友發信息,但是要加密的。加密方案是在每個單詞前都有‘<3’,最後一個單詞之後還有一個'<3',他想要發的短信是加完'<3'之後的一個串。

現在再給你一個串,判斷這個串裏是不是完全包含上面那個加密後的串,如果包含yes否則no。

做法:構造好加密好的串,一位一位的比較就可以了。

#include<cstdio>
#include<algorithm>
#include<iostream>
#include<string>
#include<cstring>
#include<cmath>
#include<queue>
#include<vector>
using namespace std;
int n;
char a[1000006],b[1000006],s[100005];
int main(){
    int l = 0;
    cin>>n;
    a[l++] = '<';a[l++] = '3';
    for (int i = 0; i < n; i++)
    {
        scanf("%s",s);
        for (int j = 0; s[j] ; j++)
        {
            a[l++] = s[j];
        }
        a[l++] = '<';a[l++] = '3';
    }
    scanf("%s",b);
    int len = strlen(b);
    int k = 0;
    for (int i = 0; i < len; i++)
    {
        if(b[i] == a[k])k++;
    }
    puts(k == l?"yes":"no");
    return 0;
}


C:

題意:主角要聽從女朋友的命令,女朋友有兩種命令,一種是非0,一個是0.有三個container:queue,stack,deck,如果是非0的命令,就要求主角把這個數字加入一種容器裏,如果是0的命令,就要求從容器中取出一個數,然後清空三個容器。要求從容器裏取出的數的和是最大的(因爲取出數的和是女朋友親他的數目)。

做法:如果兩個0命令之間的非0數字不大於3,就可以把三個容器一個一個的加進去,然後pop掉。

如果大於三,就要先找出最大的三個,分別加到三個容器的front,剩下的加到deck的back。找最大的三個,我是用優先隊列找的。

#include<cstdio>
#include<algorithm>
#include<iostream>
#include<string>
#include<cstring>
#include<cmath>
#include<queue>
#include<vector>
#include<stack>
#include<functional>
using namespace std;
#define maxn 3005
int a[100005];
struct node{
	int l,n;	
}b[100005];
priority_queue<int> Q;
int main(){
	int n,ind;
	while(cin>>n){
		ind = 0;
		for (int i = 0; i < n; i++)cin>>a[i];
		int num = 0,l = 0;
		if(a[0] == 0)b[ind++].n = 0,l = 1;
		else num++;
		for (int i = 1; i < n; i++)
		{
			if(a[i] == 0)b[ind].l=l,b[ind++].n = num,num = 0,l = i+1;
			else num++;
		}
		int ff = 0;
		while(!Q.empty())Q.pop();
		int x,y,z;
		for (int i = 0; i < ind; i++)
		{
			if(b[i].n == 0){puts("0");continue;}
			else if(b[i].n == 1){
				puts("pushStack");
				printf("1 popStack\n");
			}else if(b[i].n == 2){
				puts("pushStack");puts("pushQueue");
				printf("2 popStack popQueue\n");
			}else{
				while(!Q.empty()){Q.pop();}
				for (int j = 0; j < b[i].n; j++)Q.push(a[b[i].l+j]);
				ff = 0;
				while(ff < 3){
					for (int j = 0; j < b[i].n; j++)
					{
						if(ff == 0){
							if(Q.top() == a[b[i].l + j]){
								Q.pop();x = j;
								ff++;
								continue;
							}
						}else if(ff == 1){
							if(Q.top() == a[b[i].l + j]){
								Q.pop();y = j;
								ff++;
								continue;
							}
						}else if(ff == 2){
							if(Q.top() == a[b[i].l + j]){
								Q.pop();z = j;
								ff++;
								break;
							}
						}
					}
				}
				for (int j = 0; j < b[i].n; j++)
				{
					if(j == x){
						puts("pushStack");
					}else if(j == y){
						puts("pushQueue");
					}else if(j == z){
						puts("pushFront");
					}else puts("pushBack");
				}
				printf("3 popStack popQueue popFront\n");
			}
		}
		if(num){
			for (int i = 0; i < num; i++)
			{
				puts("pushStack");
			}
		}
	}
	return 0;
}


D:

題意:主角女朋友要喂排成一列的兔子,兔子被喂到時有三種happy值,一種是它旁邊的兩個兔子都沒被喂,一種是之前有一個被餵過,一種是左右兩個之前都被喂到了。

思路:

/*
So when I am at a particular hare I should know if I have fed the previous hare and I have to make a decision for the current one that whether it should be fed now or after the next hare
So state would be like ( int position, bool previous )
if previous is true (previous hare is already fed) :

 1. I can feed the current hare now so result1= solve( position+1, 1)+ b[position]
 2. I will feed after the next one so  result2 =  solve( position+1, 0)+ c[position]
 

Else if previous is false (previous hare is not fed)

 1. I can feed the current hare now so result1= solve( position+1, 1)+ a[position]
 2. I will feed after the next one so  result2 =  solve( position+1, 0)+ b[position]

  return max(result1,result2)
*/
#include<cstdio>
#include<algorithm>
#include<iostream>
#include<string>
#include<cstring>
#include<cmath>
#include<queue>
#include<vector>
using namespace std;
#define maxn 3005
int n;
int a[maxn],b[maxn],c[maxn],dp[maxn][2];
int main(){
    while(cin>>n){
        for (int i = 0; i < n; i++)cin>>a[i];
        for (int i = 0; i < n; i++)cin>>b[i];
        for (int i = 0; i < n; i++)cin>>c[i];
        memset(dp,0,sizeof(dp));
        dp[n-1][0] = a[n-1];dp[n-1][1] = b[n-1];
        for (int i = n-2; i >= 0; i--)
        {
            dp[i][0] = max(a[i]+dp[i+1][1],b[i]+dp[i+1][0]);
            dp[i][1] = max(b[i]+dp[i+1][1],c[i]+dp[i+1][0]);
        }
        cout<<dp[0][0]<<endl;
    }
    return 0;
}



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章