7-11 郁闷的语文课代表分数 25(C++)

三青化十大学是一所著名的大学,有着数以万计的学生。作为语文课代表,我的任务之一便是统计每位学生的试卷分数。这本来是一份不错的工作,但是令人郁闷的是,我们的孙老师为了让学生不断练习,经常给学生发卷子。如果她心情好,就给所有学生发相同数量的卷子。反之,如果心情不好,就可能收所有学生相同数量的卷子。由于她判不完这些卷子,因此学生在一段时间内都没法拿到这些卷子。

频繁收发卷子很让学生反感,尤其是收卷子的时候,一旦某位学生发现自己手中卷子数量已经低于了一名好学生应有的卷子数量,他就会立刻气愤地离开三青化十大学,并且加入北京大学邮电分校。每当一位学生离开学校,我就要从电脑中把他的学籍删去,同样,每当一名新的学生加入学校,我就得为他新建一个学籍。

孙老师经常到我这边来询问学生的情况,她并不问具体某位学生的试卷情况,而是问现在试卷数量第k多的学生手中有多少卷子。每当这时,我就不得不对数万名学生进行一次漫长的排序,然后告诉她答案。

好了,现在你已经对我的工作了解不少了。正如你猜的那样,我想请你编一个统计程序。怎么样,不是很困难吧?如果某个学生的初始试卷数量低于一名好学生应有的卷子数量,那么将不计入最后的答案内

输入格式:

第一行有两个非负整数n和min。n表示下面有多少条命令,min表示一名好学生应有的卷子数量。

接下来的n行,每行表示一条命令。命令可以是以下四种之一:

名称 格式 作用

I命令 I_k 新建一个学生学籍,初始试卷数为k。如果某学生的初始试卷数低于一名好学生应有的卷子数量,他将立刻离开学校。

A命令 A_k 给每位学生发数量k的卷子

S命令 S_k 收每位学生数量k的卷子

F命令 F_k 查询第k多的试卷数量

_(下划线)表示一个空格,I命令、A命令、S命令中的k是一个非负整数,F命令中的k是一个正整数。

在初始时,可以认为学校里一个学生也没有。

输出格式:

输出文件的行数为F命令的条数加一。

对于每条F命令,你的程序要输出一行,仅包含一个整数,为当前试卷数量第k多的学生所拥有的试卷数,如果k大于目前学生的数目,则输出-1。

输出文件的最后一行包含一个整数,为离开学校的学生的总数。

输入样例:

在这里给出一组输入。例如:

9 10
I 60
I 70
S 50
F 2
I 30
S 15
A 5
F 1
F 2

输出样例:

在这里给出相应的输出。例如:

10
20
-1
2

说明:

I命令的条数不超过100000

A命令和S命令的总条数不超过100

F命令的条数不超过100000

每次收发卷子数量不超过1000

新学生的试卷数量不超过100000

代码长度限制

16 KB

时间限制

1000 ms

内存限制

256 MB

 

#include<bits/stdc++.h>
using namespace std;
#define int long long
#define pb push_back
#define IOS ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);
int dir[4][2]={-1,0,0,-1,1,0,0,1};
const int N = 1e6+10;
int n,m,k,T;
signed main(){
    cin >> n >> m;
    char op;int a ;
    vector<int>v;
//使用vector维护一个递增区间,如果一直排序肯定会超时 
    int cnt = 0 ;
    for(int i=1;i<=n;i++){
        cin >> op >> a ;
        if(op=='I'){
        	if(a<m)continue;
        	//如果一个人初始值小于最小值直接跳过 
            auto j = upper_bound(v.begin(),v.end(),a);
            //获取vector中第一个大于插入值的地址 
			v.insert(j,a);
			//进行插入操作 
        }else if(op == 'A'){
        	//增加卷子 
            for(int j=0;j<v.size();j++){
                v[j]+=a;
            }
        }else if(op == 'S'){
            int tmp;
            tmp= lower_bound(v.begin(),v.end(),a+m)-v.begin();
			//获取即将离开学校的人数 
			cnt+=tmp;
            v.erase(v.begin(),v.begin()+tmp);
            //删除 
            for(int j=0;j<v.size();j++){
                v[j]-=a;
            }
            //减去卷子 
        }else{
            if(a>v.size()){
                cout << -1 << endl;
            }else{
                cout << v[v.size()-a] << endl;
            }
        }
    }
    cout << cnt << endl;
    //输出 
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值