深渊–C语言实现
深渊
当你凝视深渊时,深渊也在凝视你 (尼采)
今晚深渊结算!为了遏止大家过分地内卷,
圣芙蕾雅的学园长,天命组织的少当家,煌帝国的掌权者,出逃的吸血鬼——
年近五旬的德丽莎·阿波卡利斯
发明了一套新的深渊机制,即:
大家按照序号从小到大排成一队 两两为组 互相比较欧气程度
欧气大的那个人胜出 (呜呜呜)
胜出的人继续按照这套办法两两为组比较
直到决出最欧的那一个
德丽莎指出:“因为怕麻烦,你们的欧气都不一样哦”
最后,因为大家都不喜欢最欧的人,于是学园长决定把奖励给第二欧的那位——你的任务是,告诉学园长,谁才是这个学院第二欧的人?
输入格式:
第一行: 一个整数 n , n的取值在 [ 1 , 7 ] ;
表示一共有 2的n次位舰长进入了深渊。
第二行: 2的n次个互不相等的整数a;
表示舰长们的欧气值,第 i 位舰长的欧气值为 ai;
输出格式:
一个整数,表示第二欧的人在输入顺序里的位次 i .
输入样例:
2
1 4 5 3
输出样例:
在这里给出相应的输出。例如:
2
样例解释:
位次: 1 2 3 4
欧气: 1 4 5 3
第一次比较: (1,4)-> 4 ; (5,3)-> 5 ;
第二次比较: (4,5)-> 5; 第二欧的是 位次为2 欧气为4 的舰长
解题思路:
首先是当n=1的时候也就是只有两个数据,做特殊处理,找到小的即可.
用两个数组,max和num分别记录两两比较时大的那个,和大的那个的位置,这里要注意:“k”是每次循环结束都会重置为0,它的用处就是覆盖掉原本a[]的元素,每次循环后剩下的都是经过比较的.
而“j”是不会重置的,它每次都++,哪怕循环结束也一样,这样有个好处就是会记录每一次比较后大的的位置,当进行到了最后一次比较,倒数第二大的元素的位置就会被记录在num数组的倒数第3位 ,大家可以自己写一下试试看 .
发现不是这样,修改了一下,最后比较a[0] a[1]即可,因为最后选出来的两个数被记录在了0 和1,然后再决定输出倒数第二个num[]还是倒数第三个num[]
因为是两个两个比较,所以循环的时候i每次+2就好
#include<stdio.h>
#include<math.h>
#include <string.h>
#include <stdlib.h>
int cmp(const void *a,const void *b)
{
return (*(int *)a-*(int *)b);
}
int main()
{
/*int i=0,s[10000],n,t[200],k=0,p,a[200],max[200],j=0,num[200];
scanf("%d",&n);
p=n;
for(i=0;i<pow(2,n);i++)
{
scanf("%d",&a[i]);
t[i]=i;
max[i]=a[i];
num[i]=i;
}
qsort(a,pow(2,n),sizeof(a[0]),cmp);
i=0;
p=pow(2,n)-2;
for(i=0;i<pow(2,n);i++)
{
if(a[p]==max[i])
{
printf("%d",num[i]+1);
}
}
*/
int i=0,n,t[200],k=0,p,a[200],max[200],j=0,num[200];
scanf("%d",&n);
p=n;
for(i=0;i<pow(2,n);i++)
{
scanf("%d",&a[i]);
t[i]=i;
}
if(n==1)
{
i=0;
if(a[i]>a[i+1])
{
printf("2");
return 0;
}
else{
printf("1");
return 0;
}
}
i=0;
while(pow(2,n)!=1)
{
if(a[i]>a[i+1])
{
a[k]=a[i];
num[j]=t[i];
t[k]=num[j];
}
else{
a[k]=a[i+1];
num[j]=t[i+1];
t[k]=num[j];
}
j++;
i=i+2;
k++;
if(i==pow(2,n))
{
i=0;
n--;
k=0;
}
}
p=pow(2,p)-4;
if(a[0]>a[1])
{
printf("%d",num[p+1]+1);
}
else
printf("%d",num[p]+1);
return 0;
}