前天花了一下午(大概四个多小时吧)品尝了一些985高校的新生赛题目,比我们学校的题目难多了(可能是我太菜了hhh),总而言之,发现题目综合性很强,重点考察思维和逻辑,以此写写博客记录一下,以后有时间再补补其他题目(n年后)
B - The Secret of Time
题目贴上:
真·签到题(比较经典的签到题)
题意: 让你找一个数n,其平方数是16位,而且必须满足一下条件(第一位是1,第三位是9,第五位2,第七位6,第九位0,第十一位8,第十三为1,第十五位7),随便输出一个符合条件的n
思路: 背后偷偷暴力枚举,再输出就可以了
#include<bits/stdc++.h>
#define p(a,b) pow(a,b)
using namespace std;
typedef unsigned long long ll;
const int MAX = 2e5+12;
int visit[MAX];
bool isOk(ll n)
{
ll sum;
for(ll i=10000001;i<=100000001;i+=10){
sum = i*i;
//cout<<sum<<endl;
if(isOk(sum)){
cout<<i<<endl;
return 0;
}
}
n /=100;
if(n%10!=9) return false;//14
n /=100;
if(n%10!=2) return false;//12
n /=100;
if(n%10!=6) return false;//10
n /=100;
if(n%10!=0) return false;//8
n /=100;
if(n%10!=8) return false;//6
n /=100;
if(n%10!=1) return false;//4
n /=100;
if(n%10!=7) return false;//2
return true;
}
int main(void)
{
cout<<93389411<<endl;
}
D - 元素周期表(我见到最恶心的题目之一)
题目大意: 给你一个简易的分子式,求它的相对分子质量(所有原子的相对原子质量之和)
思路: 真就一个一个列呗,用map映射就可以,注意分子式的判断就可以,不难
#include<bits/stdc++.h>
#define p(a,b) pow(a,b)
#define m(a,b) ((a)>(b)?(a):(b))
using namespace std;
typedef long long ll;
const int MAX = 2e5+12;
const int N = 1e6+10;
map<string,double> num;
void init()
{
num["H"]=1.008;
num["He"]=4.003;num["Li"]=6.941;
num["Be"]=9.012;num["B"]=10.81;
num["C"]=12.01;num["N"]=14.01;
num["O"]=16;num["F"]=19;
num["Ne"]=20.18;num["Na"]=22.99;
num["Mg"]=24.31;num["Al"]=26.98;
num["Si"]=28.09;num["P"]=30.97;
num["S"]=32.07;num["Cl"]=35.45;
num["Ar"]=39.95;num["K"]=39.1;
num["Ca"]=40.08;num["Sc"]=44.96;
num["Ti"]=47.88;num["V"]=50.94;
num["Cr"]=52;num["Mn"]=54.94;
num["Fe"]=55.85;num["Co"]=58.93;
num["Ni"]=58.69;num["Cu"]=63.55;
num["Zn"]=65.39;num["Ga"]=69.72;
num["Ge"]=72.59;num["As"]=74.92;
num["Se"]=78.96;num["Br"]=79.9;
num["Kr"]=83.8;num["Rb"]=85.47;
num["Sr"]=87.62;num["Y"]=88.91;
num["Zr"]=91.22;num["Nb"]=92.91;
num["Mo"]=95.94;num["Tc"]=97.91;
num["Ru"]=101.1;num["Rh"]=102.9;
num["Pd"]=106.4;num["Ag"]=107.9;
num["Cd"]=112.4;num["In"]=114.8;
num["Sn"]=118.7;num["Sb"]=121.8;
num["Te"]=127.6;num["I"]=126.9;
num["Xe"]=131.3;num["Cs"]=132.9;
num["Ba"]=137.3;num["La"]=138.9;
num["Ce"]=140.1;num["Pr"]=140.9;
num["Nd"]=144.2;num["Pm"]=144.9;
num["Sm"]=150.4;num["Eu"]=152;
num["Gd"]=157.3;num["Tb"]=158.9;
num["Dy"]=162.5;num["Ho"]=164.9;
num["Er"]=167.3;num["Tm"]=168.9;
num["Yb"]=173;num["Lu"]=175;
num["Hf"]=178.5;num["Ta"]=180.9;
num["W"]=183.9;num["Re"]=186.2;
num["Os"]=190.2;num["Ir"]=192.2;
num["Pt"]=195.1;num["Au"]=197;
num["Hg"]=200.6;num["Tl"]=204.4;
num["Pb"]=207.2;num["Bi"]=209;
num["Po"]=209;num["At"]=210;
num["Rn"]=222;num["Fr"]=223;
num["Ra"]=226;num["Ac"]=227;
num["Th"]=232;num["Pa"]=231;
num["U"]=238;num["Np"]=237.1;
num["Pu"]=244.1;num["Am"]=243.1;
num["Cm"]=247.1;num["Bk"]=247.1;
num["Cf"]=252.1;num["Es"]=252.1;
num["Fm"]=257.1;num["Md"]=258.1;
num["No"]=259.1;num["Lr"]=262.1;
num["Rf"]=265.1;num["Db"]=268.1;
num["Sg"]=271.1;num["Bh"]=270.1;
num["Hs"]=277.2;num["Mt"]=276.2;
num["Ds"]=281.2;num["Rg"]=280.2;
num["Cn"]=285.2;num["Nh"]=284.2;
num["Fl"]=289.2;num["Mc"]=288.2;
num["Lv"]=293.2;num["Ts"]=294.2;
num["Og"]=294.2;
}
int a[N];
int main()
{
string s;
int t;
scanf("%d",&t);
init();
while(t--)
{
string mid="";
cin>>s;
double sum=0;
for(int i=0;i<s.size();++i){
if(isupper(s[i])){
mid="";
mid+=s[i];
if(i==s.size()-1) {
sum+=num[mid];break;}
if(isupper(s[i+1]))
sum+=num[mid];
else if(islower(s[i+1])){
mid+=s[i+1];
if(i==s.size()-1) {
sum+=num[mid];break;}
if(!isdigit(s[i+2]))
sum+=num[mid];
++i;
}
}else if(isdigit(s[i])){
int ans=0;
ans = ans*10+s[i]-'0';
for(int j=i+1;j<=i+5;++j){
if(isdigit(s[j]))
ans = ans*10+s[j]-'0';
else {
sum+=ans*num[mid];i=j-1;break;}
}
}
}
printf("%.4lf\n",sum);
}
return 0;
}
F - 浴缸
题目大意: 给定浴缸里面高低层次结构和注入水的体积,问你注入完这么多水后水平面距离浴缸顶部的距离是多少
思路: 没什么办法,结构自己脑补就可以做出来
#include<bits/stdc++.h>
#define p(a,b) pow(a,b)
#define m(a,b) ((a)>(b)?(a):(b))
using namespace std;
typedef long long ll;
const int N = 1003;
int a[N*N],visit[105]={
0};
struct Point{
int value=0;
ll num=0;
}p[105];
bool cmp(const Point&a,const Point&b){
return a.value>b.value;//&&a.num!=0&&b.num!=0;
}
void debug(int h){
for(int i=1;i<=h;++i){
cout<<p[i].value<<" "<<p[i].num<<endl;
}
}
int main()
{
int h = -1,n,m,v,c=0,top=0;
scanf("%d%d%d",&n,&m,&v);
for(int i=1;i<=n*m;++i){
scanf("%d",&a[i]);
h = m(h,a[i]);
p[a[i]].value = a[i];
p[a[i]].num+=1;
}
//debug(h);
sort(p+1,p+h+1,cmp);
//debug(h);
for(int i=2;i<=h;++i)
p[i].num+=p[i-1].num;
//debug(h);
int now_h = 0;
for(int i=1;i<=h;++i){
if(p[i].num==0) continue;
if(v/p[i].num==1){
now_h = h - p[i].value + 1;
break;
}else v -= p[i].num;
}
printf("%d",h-now_h);
return 0;
}
G - 伙伴系统
题目大意: 你可以通过free申请一定空间的内存块,通过allocate使用你已经申请的空闲内存快,如果每次操作合法就打印执行本次操作后十一处内存块被申请的数量,非法就输出ERROR!
思路: 纯粹二进制的题目,没什么好说的
#include<bits/stdc++.h>
#define p(a,b) pow(a,b)
#define m(a,b) ((a)>(b)?(a):(b))
using namespace std;
typedef long long ll;
const int MAX = 2e5+12;
const int N = 1e6+10;
ll sum=0;
ll d,c=0,a[13],m[13],check[13]={
0};
void getCheck()
{
check[0]=1;
for(int i=1;i<11;++i)
check[i] = check[i-1]*2;
}
void getEJ(ll top)
{
memset(a,0,sizeof a);
c = 0;
while(top){
a[++c]=top%2;
top/=2;
}
}
void FREE(ll k)
{
getEJ(k);
for(int i=1;i<=11;++i){
m[i]+=a[i];
if(i==1) printf("%d",m[i]);
else printf(" %d",m[i]);
}
printf("\n");
}
void AllOCATE()
{
bool is = false;
int i;
for(i=1;i<=11;++i){
if(m[i]>0 && check[i-1]>=d){
is = true;
break;
}
}
if(!is){
printf("ERROR!\n");return;}
m[i]-=1;
FREE(check[i-1]-d);
}
int main()
{
char str[15];
int t;
scanf("%d",&t);
getchar();
getCheck();
while(t--){
scanf("%s%d",str,&d);
switch(str[0]){
case 'a':
AllOCATE();
break;
case 'f':
FREE(d);
break;
}
}
return 0;
}
J - 机房的圣诞礼物(签到题)贪心
题意: 给你一系列带编号的盒子,盒子上面有号码,你可以选取一些盒子,但是你选取的集合里面不能出现两个互偶的编号(比如你选择了n,不能选2n,比如你选了n,不能选2/n),问你怎么选使你的盒子集合编号和最大
思路: 如果从前往后遍历,肯定是选了小的丢了大的,不符合,反过来选就可以了,肯定最大
#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
const int MAX = 2e5+12;
int visit[MAX];
int main(void)
{
int n;
cin>>n;
ll sum = 0;
for(int i=n;i>=1;--i){
if(visit[i]==0){
sum += i;
if(i%2==0)
visit[i/2]=1;
}
}
cout<<sum<<endl;
return 0;
}
M - 长安街的华灯(数学题)
题意: 一条直线上面有n个路灯,路灯的照亮范围是以R为半径圆的面积,问你给定一系列灯的照亮半径,灯数量,灯的间距(相邻灯间距相等),求灯照亮的最大范围。
思路: 没什么办法,数学公式推(相离,内含,相交什么的),注意边界为0的各种情况就可以
我自己推了一下,两种情况答案是一样的
#include<bits/stdc++.h>
#define p(a,b) pow(a,b)
#define m(a,b) ((a)>(b)?(a):(b))
using namespace std;
typedef long long ll;
typedef long double db;
const double PI = acos(-1.0);
const int MAX = 2e5+12;
const int N = 1e6+10;
int n;
double r,d;
double getJS() //求两圆相交面积
{
if(d>=2*r) return 0; //相离或外切
double sin_r = sqrt(1.0-d*d/(4*r*r));
double acos_r = acos(d/(2*r));
return 2*r*r*acos_r - d*r*sin_r;
}
int main()
{
int t;
cin>>t;
while(t--){
scanf("%d%lf%lf",&n,&r,&d);
double s = n*PI*r*r;
double pres = getJS();
if(n==0 || r==0){
cout<<"0"<<endl;continue;}
if(d==0 || n==1) printf("%.6lf\n",PI*r*r);
else
//cout<<s-pres*(n-1)<<endl;
printf("%.6lf\n",s-pres*(n-1));
}
//cout<<1.0-(8.8812615/8.881262)<<endl;
return 0;
}//8.8812615
//0.0000005 = 5x10^(-7)
//1-b/a = 1 - (8.8812615/8.881262);
注:虽然每个人大学起点不一样,但只要努力,我们就一定可以慢慢拉平差距,共勉!!!