描述:
突发重大灾难,n个人陷入困境,有一个救援点需要人们排队准备接受救援,假设每个人有一个名望值,进队规则如下:
- 第一个人直接进队;
- 当队里已经有人时,新来的人发现队尾的人的名望值比自己大或者相等,他会选择离开去其他救援点;
- 队伍最多5人,如果一个人要进队时,发现队伍已满,而且他的名望值比队尾的人大,他会选择把队首的人挤掉而继续排在队尾。
问最后得到救援的人分别是谁。
输入
单组数据。
第一行为n(1 ≤ n ≤ 100),n为正整数。
第二行为n个人的名望值,第i个去排队的人的名望值为ai (1 ≤ ai ≤ 232 - 1),且为正整数。
输出
按顺序输出最后得到救援的人的号码,一个人号码是多少即为他是第几个去排队的。
输入样例
6
1 3 5 7 9 11
输出样例
2 3 4 5 6
题目分析:
该题需要用到队列,根据题目条件进行相关的分类即可
当一个新元素想要进入队列时,分为三种情况
①队列为空时,直接入队
②队列未满时(大小 <5),且新元素的大小 >队尾元素大小 ,新元素入队
③队列已满时,且新元素的大小 >队尾元素大小,队头元素出队,新元素入队
#include<iostream>
#include<string>
#include<queue>
using namespace std;
struct people
{
int value;//声望值
int number;//号码
};
int main()
{
int n;
cin >> n;
people p[100];
for (int i = 0; i < n; i++)
{
cin >> p[i].value;
p[i].number = i + 1;
}
queue<people> q;
//进行入队操作
for (int i = 0; i < n; i++)
{
if (q.empty()) q.push(p[i]);
else if (q.size() < 5 && q.back().value < p[i].value) q.push(p[i]);
else if(q.size()==5 && q.back().value < p[i].value)
{
q.pop();
q.push(p[i]);
}
}
//输出队列
while (!q.empty())
{
cout <<q.front().number << " ";
q.pop();
}
return 0;
}
P.S:
当考试中需要自己手动实现队列的时候,可以通过数组实现或者链表实现
队列的链式存储:
struct Node
{
int item;
Node* next;
};
struct queue
{
Node* first;//队头指针
Node* last;//队尾指针
int num;
};
相关函数:
bool isEmpty(queue q)
{
return q.first == NULL;//队列初始化时,头指针和尾指针都为空
}
void enqueue(queue &q, int n)
{
Node* oldlast = q.last;//先拿到原先的尾指针,后续操作需要用到
Node* newlast = new Node();
newlast ->item = n;
q.last = newlast;
newlast ->next = NULL;
if (isEmpty(q)) q.first = q.last;//当队列为空时,元素入队后,头指针和尾指针都指向这个元素
else
oldlast ->next = newlast;//正常情况下,需要修改原先的尾指针
q.num++;
}
int dequeue(queue& q)
{
int item = q.first->item;
q.first = q.first->next;
if (isEmpty(q)) q.last = NULL;//最后一个元素出队以后,队列变为空,尾指针要手动置空
q.num--;
return item;
}