2015年第六届(C/C++)B组蓝桥国赛题


标题:积分之迷

小明开了个网上商店,卖风铃。共有3个品牌:A,B,C。
为了促销,每件商品都会返固定的积分。

小明开业第一天收到了三笔订单:
第一笔:3个A + 7个B + 1个C,共返积分:315
第二笔:4个A + 10个B + 1个C,共返积分:420
第三笔:A + B + C,共返积分....

你能算出第三笔订单需要返积分多少吗?

请提交该整数,不要填写任何多余的内容。


105


标题:完美正方形

如果一些边长互不相同的正方形,可以恰好拼出一个更大的正方形,则称其为完美正方形。

历史上,人们花了很久才找到了若干完美正方形。比如:如下边长的22个正方形
2 3 4 6 7 8 12 13 14 15 16 17 18 21 22 23 24 26 27 28 50 60
如【图1.png】那样组合,就是一种解法。此时,
紧贴上边沿的是:60 50
紧贴下边沿的是:26 28 17 21 18

22阶完美正方形一共有8种。下面的组合是另一种:
2 5 9 11 16 17 19 21 22 24 26 30 31 33 35 36 41 46 47 50 52 61
如果告诉你该方案紧贴着上边沿的是从左到右依次为:47 46 61,
你能计算出紧贴着下边沿的是哪几个正方形吗?

请提交紧贴着下边沿的正方形的边长,从左到右,用空格分开。

不要填写任何多余的内容或说明文字。

代码:

#include<bits/stdc++.h>
using namespace std;
int maze[160][160];
int a[19]= {2,5,9,11,16,17,19,21,22,24,26,30,31,33,35,36,41,50,52};
int book[25];
void init()
{
	for(int i =1;i<=47;i++)
		for(int j = 1;j<= 47;j++)
			maze[i][j] = 47;
			
	for(int i =1;i<=46;i++)
		for(int j = 48;j<=47+46;j++)
			maze[i][j] = 46;
			
	for(int i = 1;i<=61;i++)
		for(int j = 46+47+1;j<=46+47+61;j++)
			maze[i][j] = 61;
}//初始化这个矩阵上面的表示已经被填充了 
bool check(int x,int y,int k)
{
	for(int i=x;i<=x+k-1;i++)
		for(int j = y;j<=y+k-1;j++)
			if(maze[i][j]!=0)
				return false;
	return true;
}//判断下这些地方是否都是0 这样子才能用 
void output()
{
	for(int i =1;i<=154;i++)
	{
		for(int j = 1;j<=154;j++)
			printf("%2d ",maze[i][j]);
		putchar('\n');
	}
}//输出 
void DFS(int x,int y)
{
	if(x>154){
		output();
		return;
	}
	if(maze[x][y]!=0)
	{
		if(y==154)DFS(x+1,1);
		else DFS(x,y+1);
	}else //这个地方没有东西,可以填充东西 
	{
		for(int i = 0;i<19;i++)
		{
			if(book[i]==1)continue;//这个正方形已经被使用过了
			if(x+a[i]-1>154||y+a[i]-1>154||check(x,y,a[i])==false)continue; 
		
			
			for(int k = x;k<x+a[i];k++)
			{
				for(int l = y;l<y+a[i];l++)
					maze[k][l] =a[i];
			}	
			book[i] = 1;
			
			if(y==154)DFS(x+1,1);
			else DFS(x,y+1);
			
			book[i] = 0; 
			for(int k = x;k<x+a[i];k++)
			{
				for(int l = y;l<y+a[i];l++)
					maze[k][l] = 0;
			}	
		}
	}
	return ;
}
int main()
{
	freopen("C:\\Users\\DELL\\Desktop\\b.txt","w",stdout); 
	init();
	DFS(47,48);
	return 0;
}



标题:关联账户

为增大反腐力度,某地警方专门支队,对若干银行账户展开调查。

如果两个账户间发生过转账,则认为有关联。如果a,b间有关联, b,c间有关联,则认为a,c间也有关联。

对于调查范围内的n个账户(编号0到n-1),警方已知道m条因转账引起的直接关联。

现在希望知道任意给定的两个账户,求出它们间是否有关联。有关联的输出1,没有关联输出0

小明给出了如下的解决方案:

#include <stdio.h>
#define N 100

int connected(int* m, int p, int q)
{
    return m[p]==m[q]? 1 : 0;
}

void link(int* m, int p, int q)
{
    int i;
    if(connected(m,p,q)) return;
    int pID = m[p];
    int qID = m[q];
    for(i=0; i<N; i++) _____________________________________;  //填空位置
}

int main()
{
    int m[N];
    int i;
    for(i=0; i<N; i++) m[i] = i; //初始状态,每个节点自成一个连通域
    link(m,0,1); //添加两个账户间的转账关联
    link(m,1,2);
    link(m,3,4);
    link(m,5,6);
    link(m,6,7);
    link(m,8,9);
    link(m,3,7);
    
    printf("%d ", connected(m,4,7));
    printf("%d ", connected(m,4,5));
    printf("%d ", connected(m,7,9));
    printf("%d ", connected(m,9,2));
    return 0;
}


请分析源代码,并提交划线部分缺少的代码。不要填写已有代码或任何多余内容。

if(m[i]==pID)m[i]=qID



标题:密文搜索

福尔摩斯从X星收到一份资料,全部是小写字母组成。
他的助手提供了另一份资料:许多长度为8的密码列表。
福尔摩斯发现,这些密码是被打乱后隐藏在先前那份资料中的。

请你编写一个程序,从第一份资料中搜索可能隐藏密码的位置。要考虑密码的所有排列可能性。

数据格式:

输入第一行:一个字符串s,全部由小写字母组成,长度小于1024*1024
紧接着一行是一个整数n,表示以下有n行密码,1<=n<=1000
紧接着是n行字符串,都是小写字母组成,长度都为8

要求输出:
一个整数, 表示每行密码的所有排列在s中匹配次数的总和。

例如:
用户输入:
aaaabbbbaabbcccc
2
aaaabbbb
abcabccc

则程序应该输出:
4

这是因为:第一个密码匹配了3次,第二个密码匹配了1次,一共4次。


资源约定:
峰值内存消耗 < 512M
CPU消耗  < 3000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。

注意: main函数需要返回0
注意: 只使用ANSI C/ANSI C++ 标准,不要调用依赖于编译环境或操作系统的特殊函数。
注意: 所有依赖的函数必须明确地在源文件中 #include <xxx>, 不能通过工程设置而省略常用头文件。

提交时,注意选择所期望的编译器类型。



代码:

#include<bits/stdc++.h> 
using namespace std;
typedef long long ll;
const int maxn=1024*1024+10; 
char str[maxn];
struct node
{
	char ch;
	int cnt;
}gg[15];
map<char,int>hh;
map<string,int>mp;
bool cmp(node a,node b){
	return a.ch<b.ch;//从小到大的字符 
}
int main()
{
	scanf("%s",str+1);
	int len = strlen(str+1);
	int n; scanf("%d",&n);
	char xixi[10];
	if(len<8)
	{
		printf("0\n");
		return 0;
	}
	int now=0;
	for(int i=1;i<=8;i++)
		hh[str[i]]++;
	map<char ,int >::iterator it=hh.begin();
	while(it!=hh.end())
	{
		gg[++now].ch=it->first;
		gg[now].cnt=it->second;
		it++;
	}
	sort(gg+1,gg+1+now,cmp);
	
	string a;
	for(int i=1;i<=now;i++)
	{
		a+=gg[i].ch;
		a+=(gg[i].cnt+'0');
	}	//ok  初始条件已经完成 
	mp[a]++; 
	for(int i=2;i<=len;i++)
	{ 
		if(i+7<=len)
		{
			hh[str[i-1]]--;
			hh[str[i+7]]++;	 
			int now=0;
			map<char,int >::iterator iter=hh.begin();
			while(iter!=hh.end())
			{
				gg[++now].ch=iter->first;
				gg[now].cnt=iter->second;
				iter++;	
			}
			sort(gg+1,gg+1+now,cmp);
			string b;
			for(int j=1;j<=now;j++)
			{
				if(gg[j].cnt==0) continue;
				b+=gg[j].ch;
				b+=(gg[j].cnt+'0');
			}	
			mp[b]++;
		}else break;	
	}

	ll sum=0;
	map<char,int>kk;
	for(int i=1;i<=n;i++)
	{
		kk.clear();
		int now=0;
		scanf("%s",xixi);
		for(int j=0;j<8;j++)
		kk[xixi[j]]++;
		map<char,int >::iterator iter=kk.begin();
		while(iter!=kk.end())
		{
			gg[++now].ch=iter->first;
			gg[now].cnt=iter->second;
			iter++;	
		}
		sort(gg+1,gg+1+now,cmp);
		string b;
		for(int j=1;j<=now;j++)
		{
			if(gg[j].cnt==0) continue;
			b+=gg[j].ch;
			b+=(gg[j].cnt+'0');
		}
		sum=sum+mp[b];
	}
	cout<<sum<<endl;
	return 0;
}










猜你喜欢

转载自blog.csdn.net/galesaur_wcy/article/details/80368394