(2019 GDUT Rating Contest #III)F.Out of Sorts II

本文介绍了一种双向冒泡排序算法的实现,并通过分析不同位置元素的比较次数来确定最大输出次数。通过枚举和去重操作,算法能够有效解决特定排序问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

传送门

题目大意:

有一个新手小白(没错就是我)写了一个冒泡排序,问在排序的时候“moo会被输出多少次?
在这里插入图片描述

题目分析:

A题Out of Sorts的升级版
双向冒泡,一次while中,第一个for将最大元素放置末尾,第二个for将最小元素放置最前面,我们只需要枚举[0,n)的每个i,对于每一个i,找出[0,i]中不属于i位置前面(包括本身)的数的数量,即如果排在该元素前面的数不应该在该元素前面,每次双向冒泡后,都会有一个不该在它前面的数跑到它后面,找到这个值的最大值即为答案。
比如数列(8,5,4,2,1)
正确排序(1,2,4,5,8)
对于不同的i,结果分别是:1,2,2,1,0。所以最大值是2,即为答案。
还要注意去重,如果之前出现过了,就应该减去,因为它应该在的位置已经出现了。

代码:

#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cmath>
using namespace std;
const int maxn = 1e5+5;
typedef pair<int,int> P;
int vis[maxn];
bool cmp(P x,P y){
	if(x.first==y.first) return x.second<y.second;
	else return x.first<y.first;
}
P a[maxn];
int main(){
	int n,ans=1,cnt=0;
	cin>>n;
	for(int i=0;i<n;i++){
		scanf("%d",&a[i].first);
		a[i].second=i;
	}
	sort(a,a+n,cmp);
	for(int i=0;i<n;i++){
		if(i<a[i].second) cnt++;
		if(vis[i]) cnt--;			
		vis[a[i].second]=1;
		ans=max(ans,cnt);
	}
	cout<<ans<<endl;
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值