QLU迎新赛

问题 A: 约数个数
题目描述

p^ q 表示p的q次方,正整数M可以分解为M=(p1 ^ a1 )(p2 ^ a2)(p3 ^ a3)……(pn ^ an)的形式,其中p1,p2……pn为质数(大于1并且只能被1和自身整除的数叫做质数)。a1,a2……an为整数。例如18=(2 ^ 1) (3 ^ 2),45=(3 ^ 2)(5 ^ 1)。

给出n和一个质数g,以及正整数M分解后的形式,求M的所有约数中,有多少能被g整除。

输入

第一行 两个数 n和g。 0<n<=10 1<g<100。g为质数。

第二行 n个数 p1到pn 1<pi<100 pi为质数(1<=i<=n)。

第三行 n个数 a1到an 0<=ai<=20 ai为整数(1<=i<=n)。

保证对于任意的i,j(i != j) ,pi != pj

输出

一个数

表示M的所有约数中,有多少能被g整除。

样例输入

2 3
3 5
2 2

样例输出

6

提示

样例解释:

M=(3 ^ 2)(5 ^ 2)=925=225

225能被3整除的约数有3 9 15 45 75 225 共6个。

坑点:没用long long导致结果溢出
思路:把所有pi和ai各用一个数组盛起来,并在pi里找到与g相等的一项,特殊标记(假设该项为pm)。
最后结果为(a1+1) * (a2+1) * (a3+1) * … * (am) *…(ai+1)
注释1:ax+1表示px的次数可为0到ax。
注释2:am处不用+1因为g^0时的数字不是g的倍数。

#include <stdio.h>
#define INITNUM -1
int main(){
	//mark:与g相等的pi的下标,初值为INITNUM 
	int n,g,mark=INITNUM;
	//sum:总约数的个数
	//注意,不用longlong会溢出 
	long long sum=1;
	int a[11],p[11];
	scanf("%d%d",&n,&g);
	for(int i=0;i<n;i++){
		scanf("%d",&p[i]);
		//载入 p的同时寻找与g相等的项并记录下标 
		if(p[i]==g&&p[i]!=0) mark=i;
	}
	for(int i=0;i<n;i++){
		scanf("%d",&a[i]);
	}
	//下标等于初值时表明g不在p中,无解 
	if(mark==INITNUM){
		puts("0");
		return 0;
	}
	for(int i=0;i<n;i++){
		    //pi不等于g,则总约数*=(ai+1), 因为可能存在pi^0的情况 
			if(i!=mark){
				sum*=(a[i]+1);
			}
			//pi等于g,则总约数*=ai,此处不用ai+1因为g^0时的数字不是g的倍数 (前提:本题强调pi不重复) 
			else{
				sum*=(a[i]);
			}
	}
	printf("%ld",sum);
	
	return 0;
}

问题 B: Alice and Bob

题目描述
Alice and Bob decide to play a game. At the beginning of the game they put n piles of sweets on the table.The number of each pile of sweets may be different. Alice and Bob take away sweets in turn,and always Alice takes sweets first in every games.Each time in their turn they can get only one whole pile of sweets.When there is no sweet left, the game is over. Finally, The man who have the largest number of sweets in hand will win.
Assume that Alice and Bob were very clever.

输入
The first line is an integer n, which means that there are n pile sweets.
1 <= n <= 100000
Next n integers, the i-th integer means the number of sweets in the i-th pile.
The number of sweets in each pile is less than 10000.

输出
If Alice wins, output “A”, and if Bob wins, output “B”.
Otherwise output “again”

样例输入

样例输入1:
3
1 6 7

样例输入2:
4
3 3 3 3

样例输出

样例输出1:
A

样例输出2:
again

坑点:冒泡排序法超时。
卡壳原因:比赛的时候不记得快速排序的qsort函数参数是那几个了。
思路:将所有糖果堆的数量存入数组,而后降序排序。之后模拟Alice和Bob轮流拿取糖果的过程。

#include <stdio.h>
#include <stdlib.h>
int cmp(const void*a,const void*b){
	return *(int*)b-*(int*)a;
}
int main(){
	//turn:当前操作者的标记,1代表alice,0代表bob 
	int t,suma=0,sumb=0,turn=1,n,a[100002];
	scanf("%d",&n);
	for(int i=0;i<n;i++){
		scanf("%d",&a[i]);
	}
	//快速排序法生成降序序列 
	qsort(a,n,sizeof(int),cmp);
	for(int i=0;i<n;i++){
		if(turn) {
			suma+=a[i];
			turn=0;
		}
		else{
			sumb+=a[i];
			turn=1;
		}
	}
	if(suma>sumb) puts("A");
	else if(suma<sumb) puts("B");
	else puts("again");
	return 0;
}

问题 F: 折纸达人

目前错误50%,待研究出后整理

猜你喜欢

转载自blog.csdn.net/kangyupl/article/details/84559784