洛谷P1309 瑞士轮——题解
思路非常简单,只要开始时把结构体排个序,每次给赢的加分再排序,共r次,最后再输出分数第q大的就行了。
(天真的我估错时间复杂度用每次用sort暴力排序结果60分。。。)实际上这道题估算时间复杂度时O括号里的n并不是输入的n,而是输入的n乘2,这就要求我们精准地估算时间复杂度以采取合适的算法来解题。显然sort时不行的。为什么sort这么强都会TLE?考虑不行的原因,找找有用的教训:(先普及一下:sort是冒泡排序的改进版,平均时间复杂度为O(n log n),最坏情况下会退化成O(n2)。)
从sort的原理开始考虑:sort排序时会有两个指针分别从头到尾相向而行直到相遇后的分手。然后再分别对左右两部分递归,直到递归的区间长度为1。这样发现,就算这个序列已经有序(或基本有序)时,sort会造成大量的时间浪费。这时同时O(n log n)级别的归并排序就不同了。当序列基本有序时,归并排序会造成更少的时间浪费,因为序列基本有序时,“并”操作左右两区间中的左区间应该是主要都小于右区间的,这样就会使左区间更早地并入答案数组,剩下的右区间的长度相应地更长,用个memcpy就完事了,结果是使使左右区间的开头端点比较的次数减少,进而减少了时间浪费。
发现把一个大轮回比赛里的所有赢家单独拿出来后他们的顺序都是合法且不变的(因为都是从原来的序列中的相应值加1);所有输家的大小顺序也是合法的(因为值都没有改变)。这样可以直接用归并排序的思想,把赢家都放在一个区间、输家放在另一个区间中,两个区间只要归并一次就能得到有序的数列了,无需再各种递归费解合并。
见AC代码:
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cctype>
#include<cstring> using namespace std; struct hum{
int num,s,w;
}a[],win[],lose[];//赢的放一起,输的放一起 int n,r,q,ans,lw,ll; char ch; bool cmp(hum a,hum b)
{
return a.s>b.s||(a.s==b.s&&a.num<b.num);
} inline int read()
{
ans=;
ch=getchar();
while(!isdigit(ch)) ch=getchar();
while(isdigit(ch)) ans=(ans<<)+(ans<<)+ch-'',ch=getchar();
return ans;
} int main()
{
n=(read())<<,r=read(),q=read();
for(int i=;i<=n;i++)
{
a[i].num=i;
a[i].s=read();
}
for(int i=;i<=n;i++) a[i].w=read();
sort(a+,a+n+,cmp);
for(int k=;k<=r;k++)
{
for(int i=;i<=n;i+=)
{
if(a[i].w>a[i+].w)
{
a[i].s++;
win[++lw]=a[i];
lose[++ll]=a[i+];
}
else
{
a[i+].s++;
win[++lw]=a[i+];
lose[++ll]=a[i];
}
}
int l=,r=,len=;//往下都是并的过程
while(l<=lw&&r<=ll)
{
if(win[l].s>lose[r].s)
a[len++]=win[l++];
if(win[l].s<lose[r].s)
a[len++]=lose[r++];
if(win[l].s==lose[r].s)
{
if(win[l].num<lose[r].num) a[len++]=win[l++];
else a[len++]=lose[r++];
}
}
if(l<=lw) memcpy(a+len,win+l,sizeof(hum)*(lw-l+));
if(r<=ll) memcpy(a+len,lose+r,sizeof(hum)*(ll-r+));//并的过程结束
lw=;ll=; //因为是由前缀++维护,所以要初始化为1
}
cout<<a[q].num;
return ;
}
还是要做好时间复杂度估计的说!
洛谷P1309 瑞士轮——题解的更多相关文章
- 洛谷 P1309 瑞士轮 题解
每日一题 day4 打卡 Analysis 暴力+快排(其实是归并排序) 一开始天真的以为sort能过,结果光荣TLE,由于每次只更改相邻的元素,于是善于处理随机数的快排就会浪费很多时间.于是就想到归 ...
- 洛谷P1309 瑞士轮(归并排序)
To 洛谷.1309 瑞士轮 题目背景 在双人对决的竞技性比赛,如乒乓球.羽毛球.国际象棋中,最常见的赛制是淘汰赛和循环赛.前者的特点是比赛场数少,每场都紧张刺激,但偶然性较高.后者的特点是较为公平, ...
- 洛谷 P1309 瑞士轮 解题报告
P1309 瑞士轮 题目背景 在双人对决的竞技性比赛,如乒乓球.羽毛球.国际象棋中,最常见的赛制是淘汰赛和循环赛.前者的特点是比赛场数少,每场都紧张刺激,但偶然性较高.后者的特点是较为公平,偶然性较低 ...
- NOIP2011 普及组 T3 洛谷P1309 瑞士轮
今天题做太少,放道小题凑数233 题目背景 在双人对决的竞技性比赛,如乒乓球.羽毛球.国际象棋中,最常见的赛制是淘汰赛和循环赛.前者的特点是比赛场数少,每场都紧张刺激,但偶然性较高.后者的特点是较为公 ...
- 洛谷 P1309 瑞士轮
题目背景 在双人对决的竞技性比赛,如乒乓球.羽毛球.国际象棋中,最常见的赛制是淘汰赛和循环赛.前者的特点是比赛场数少,每场都紧张刺激,但偶然性较高.后者的特点是较为公平,偶然性较低,但比赛过程往往十分 ...
- 洛谷P1309——瑞士轮(归并排序)
https://www.luogu.org/problem/show?pid=1309#sub 题目背景 在双人对决的竞技性比赛,如乒乓球.羽毛球.国际象棋中,最常见的赛制是淘汰赛和循环赛.前者的特点 ...
- 洛谷P1309 瑞士轮
传送门 题目大意: 2*n个人,有初始的比赛分数和实力值. 每次比赛前总分从大到小排序,总分相同编号小的排在前面. 每次比赛是1和2比,3和4比,5和6比. 实力值大的获胜得1分. 每次比赛前排序确定 ...
- 洛谷 - P1309 - 瑞士轮 - 归并排序
https://www.luogu.org/problemnew/show/P1309 一开始写的直接快排没想到真的TLE了. 想到每次比赛每个人前移的量不会很多,但是不知从哪里开始优化. 搜索一下原 ...
- P1309 瑞士轮 (吸氧了)
P1309 瑞士轮 题解 1.这题可以模拟一下 2.sort吸氧可以过(可能是排序有点慢吧,不开会T) sort排序时注意: return 1 是满足条件,不交换 return 0是不满足,交换 代码 ...
随机推荐
- 【Qt开发】 V4L2_CAP_VIDEO_OVERLAY与V4L2_CAP_VIDEO_CAPTURE的区别
原文地址http://www.cnblogs.com/tlm1992/archive/2012/06/12/2545772.html 这部分spec的内容没有全看懂,但是根据FSL的代码能知道这其中的 ...
- 深入理解java:1.2. 字节码执行引擎
执行引擎是Java虚拟机的核心组成部分之一. 首先,想想C++和Java在编译和运行时到底有啥不一样? 下图左边,C++发布的就是机器指令, 而下图右边Java发布的是字节码,字节码在运行时通过JVM ...
- [DS+Algo] 004 栈、队列及其代码实现
1. Stack FILO (FirstInLastOut) 的链表结构 在程序编译环境上使用较多 常用操作 push pop peek is_empty size Python 代码示例 class ...
- 【C语言--数据结构】线性表链式存储结构
直接贴代码 头文件 #ifndef __LINKLIST_H__ #define __LINKLIST_H__ typedef void LinkList; typedef struct _tag_L ...
- 获取IP地址的几种方法
根据ip获取地址的几种方法 1.调用新浪IP地址库 <script type="text/javascript" src="js/jquery.js"&g ...
- python 序列解包(解压缩)
序列解包(解压缩) 所学的解压缩 如果我们给出一个列表,我们需要一次性取出多个值,我们是不是可以用下面的方式实现呢? name_list = ['nick', 'egon', 'jason'] x = ...
- set(详解)
1.关于set C++ STL 之所以得到广泛的赞誉,也被很多人使用,不只是提供了像vector, string, list等方便的容器,更重要的是STL封装了许多复杂的数据结构算法和大量常用数据结构 ...
- egg框架实现表单验证及获取验证的错误信息
最近再看egg框架 是阿里今年开源的一款基于nodejs的mvc架构的web框架 感兴趣的同学可以看看 因为之前一直做php的关系 在tp,yii,laravel这些框架中对于前台发送的数据,模型里都 ...
- GitHub入门使用
1.首先注册账号. 2.新建仓库. 3.安装GitBash 4.首先要在本地创建一个ssh key. $ ssh -keygen -t rsa -C "your email@.com&quo ...
- 吴恩达机器学习7:代价函数(Cost function)
一.简介 1.在线性回归中,我们有一个这样的训练集,M代表训练样本的数量,假设函数即用来进行预测的函数是这样的线性函数的形式,我们接下来看看怎么选择这两个参数: 2.如下图中,怎么选择两个参数来更好的 ...