2020第十一届蓝桥杯C++B组省赛第二场试题J题解

问题表示

【问题描述】
小蓝最近学习了一些排序算法,其中冒泡排序让他印象深刻。在冒泡排序中,每次只能交换相邻的两个元素。小蓝发现,如果对一个字符串中的字符排序,只允许交换相邻的两个字符,则在所有可能的排序方案中,冒泡排序的总交换次数是最少的。例如,对于字符串lan 排序,只需要1 次交换。对于字符串qiao 排序,总共需要4 次交换。
小蓝的幸运数字是V,他想找到一个只包含小写英文字母的字符串,对这个串中的字符进行冒泡排序,正好需要V 次交换。请帮助小蓝找一个这样的字符串。如果可能找到多个,请告诉小蓝最短的那个。如果最短的仍然有多个,请告诉小蓝字典序最小的那个。请注意字符串中可以包含相同的字符。
【输入格式】
输入一行包含一个整数V,为小蓝的幸运数字。以下N行,包含两个整数A,B。
【输出格式】
输出一个字符串,为所求的答案。
【样例输入】
4
【样例输出】
bbaa

初步想法

打表

第一次看到这个题的时候并没有什么想法,所以打算通过打表来尝试寻找规律。于是首先遍历了N=1-10的情况:

交换次数 字符串 变化方式
1 ba 固定
2 baa ba+a
3 cba 固定
4 bbaa b+baa
5 cbaa cba+a
6 dcba 固定
7 cbaaa cbaa+a
8 cbbaa cbaa插入b
9 dcbaa dcba+a
10 edcba 固定
打表后看到的规律
  • 每个字符串的逆序数目便等于该字符串变为有序所需要的交换次数。
  • ba,cba,dcba这种按照字母表倒序来的是固定的,对应的是(1+2+…+n-1,n-1为字符串长度)的最短冒泡排序字符串。比如:cba是1+2=3位的最短字符串。
  • 其他的最短字符串是以后的字符串在某个特定位置插入某个字符的结果。比如:交换次数为4的字符串bbaa是交换次数为2的字符串baa在头部插入b得到的。

规律2,3证明

规律2和规律3直接看起来没那么有说服力,我们通过数学上进行证明,来证明我们提出假设的有效性。

规律2的证明

假设一个字符串 s s s,字符串的长度为 1 + 2 + . . . + n 1+2+...+n 1+2+...+n,如果想要字符串的逆序数最大,每个位置的字符需要满足的条件为 s i − 1 ≥ s i ≥ s i + 1 , i > = 2 s_{i-1} \geq s_i \geq s_{i+1},i>=2 si1sisi+1,i>=2,其中 s i s_i si表示字符串 s s s i i i个位置的字符,即字符串右边的字符总是小于左边的字符。

反证法:假设当字符串长度为 1 + 2 + . . . + n = N 1+2+...+n=N 1+2+...+n=N时,保持原有字符不变,存在一个字符排列 s k s^{k} sk,使得 s k s^{k} sk的逆序数大于 s s s。因为 s k s^{k} sk s s s的字符组成都相同,那么 s k s^{k} sk是由 s s s至少交换一对字符得到的。假设交换的字符在 s s s中的位置分别是 i i i j j j,其中 i < j i<j i<

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值