问题描述
在一个整数序列a1, a2, …, an中,如果存在某个数,大于它的整数数量等于小于它的整数数量,则称其为中间数。在一个序列中,可能存在多个下标不相同的中间数,这些中间数的值是相同的。
给定一个整数序列,请找出这个整数序列的中间数的值。
输入格式
输入的第一行包含了一个整数n,表示整数序列中数的个数。
第二行包含n个正整数,依次表示a1, a2, …, an。
输出格式
如果约定序列的中间数存在,则输出中间数的值,否则输出-1表示不存在中间数。
样例输入
6
2 6 5 6 3 5
样例输出
5
样例说明
比5小的数有2个,比5大的数也有2个。
样例输入
4
3 4 6 7
样例输出
-1
样例说明
在序列中的4个数都不满足中间数的定义。
样例输入
5
3 4 6 6 7
样例输出
-1
样例说明
在序列中的5个数都不满足中间数的定义。
评测用例规模与约定
对于所有评测用例,1 ≤ n ≤ 1000,1 ≤ ai ≤ 1000。
自己写的:注意csp官网选择c语言时,按语言规范,所用到的变量必须全部在最开始就定义好,不可在循环中定义,例如for(int i=0;i<n;i++),否则提交后会显示编译错误。
#include <stdio.h>
#include <stdlib.h>
int main()
{
int n,*p=NULL,max,min=0,flag=0,i,j;
scanf("%d",&n);
p=(int*)malloc(sizeof(int)*n);
if(p==NULL)
exit(1);
for(i=0; i<n; i++)
scanf("%d",&p[i]);
for(i=0; i<n; i++)
{
max=min=0;
for(j=0; j<n; j++)
{
if(p[i]>p[j])
min++;
else if(p[i]<p[j])
max++;
}
if(max==min)
{
flag=1;
printf("%d",p[i]);
break;
}
}
if(!flag)
printf("-1");
free(p);
return 0;
}
法二:书上的(但显示编译错误)?????????????????????
#include <algorithm>
#include <cstdio>
#include <iostream>
#include <vector>
using namespace std;
int main()
{
int n;
std::vector<int> input;
std::cin>>n;
input.reserve(n);
for(int i=0; i<n; i++)
{
int in;
std::cin>>in;
input.push_back(in);
}
std::sort(input.begin(),input.end());
int possMid = -1,possMidPos = -1;
if(n%2 == 0)
{
//n是偶数
possMidPos = n/2;
if(input[possMidPos] == input[possMidPos - 1])
{
//潜在的中间数是中间两数
possMid = input[possMidPos];
}
else
{
//若中间两数不等,则排除中间数的存在
possMidPos = -1;
}
}
else
{
possMidPos = n/2;
possMid =input[possMidPos];
}
if(possMidPos != -1)
{
int startPos;
int endPos;
//向前后搜索,得到与possMidPos相等的数字区间
for(starPos = possMidPos; startPos>0; startPos--)
{
if(input[startPos - 1] != possMid)
{
break;
}
}
for(endPos = possMidPos; endPos < n; endPos++)
{
if(input[endPos] != possMid)
{
break;
}
}
//[startPos,endPos]就是所求
if(startPos != n-endPos)
{
possMidPos = -1;
}
}
if(possMidPos != -1)
{
std::cout<<possMid<<std::endl;
}
else
{
std::cout<<-1<<std::endl;
}
return 0;
}