当前位置: 首页 > article >正文

NOIP模拟赛 序列(sequence)

题目描述

给定一个 x 1 , x 2 , … , x n x_1,x_2,\dots,x_n x1,x2,,xn的序列,每次你可以将 x 1 , x 2 … , x i x_1,x_2\dots,x_i x1,x2,xi翻转,请求出将序列变为升序的最小操作次数。有多组数据。

输入格式

第一行一个整数 t t t表示数据组数。

每组数据一行一个整数 n n n,第二行 n n n个整数 x 1 , x 2 , … , x n x_1,x_2,\dots,x_n x1,x2,,xn

输出格式

每组数据输出一行一个整数表示答案。

样例输入

1
8
8 6 1 3 2 4 5 7

样例输出

7

数据范围

1 ≤ t ≤ 5 , 1 ≤ n ≤ 25 1\leq t\leq 5,1\leq n\leq 25 1t5,1n25


题解

每次将最大的没有归位的数翻转到最前面,然后再将其翻转到对应的位置,这样做的操作次数不会超过 2 n − 2 2n-2 2n2。我们只需要找到操作次数小于 2 n − 2 2n-2 2n2的做法。因为操作次数不多,所以我们可以用迭代加深搜索。

当然,还需要一些剪枝。我们发现每次翻转最多只会改变一对相邻数对,因此对于每个状态,求出其相差大于 1 1 1的相邻数对的数量,如果剩余步数小于这个值,则这种状态不可行。加上这个剪枝就能过。

code

#include<bits/stdc++.h>
using namespace std;
int T,n,fl,ans,a[35];
void dfs(int t,int now){
	if(now>ans) return;
	while(t>0&&a[t]==t) --t;
	if(t==0){
		fl=1;return;
	}
	int v=0;
	for(int i=1;i<n;i++){
		if(abs(a[i+1]-a[i])>1) ++v;
	}
	if(now+v>ans) return;
	for(int i=2;i<=t;i++){
		reverse(a+1,a+i+1);
		dfs(t,now+1);
		reverse(a+1,a+i+1);
		if(fl) return;
	}
}
int main()
{
	scanf("%d",&T);
	while(T--){
		fl=0;
		scanf("%d",&n);
		for(int i=1;i<=n;i++){
			scanf("%d",&a[i]);
		}
		for(ans=0;ans<=2*n-2;ans++){
			dfs(n,0);
			if(fl) break;
		}
		printf("%d\n",ans);
	}
	return 0;
}

http://www.kler.cn/a/4716.html

相关文章:

  • VSCode 插件
  • 【Python】数据容器:列表,元组,字符串,集合字典及通用操作
  • 计算机网络 (39)TCP的运输连接管理
  • 快速上手 INFINI Console 的 TopN 指标功能
  • nginx负载均衡-基于端口的负载均衡(一)
  • JVM:ZGC详解(染色指针,内存管理,算法流程,分代ZGC)
  • 深入分析@PropertySource源码
  • SpringBoot源码学习系列——自动配置原理(一)
  • 简单的C++程序
  • java源码阅读 - TreeMap
  • 抖音进攻,B站退守
  • 单例模式是什么?如何实现它?
  • 【华为OD机试 2023最新 】 最大利润(C++)
  • 秃头警告 | 年薪50万PM总结的20个成功项目管理经验
  • GPT4中文调教指南。各种场景使用指南。学习怎么让它听你的话。
  • NOIP模拟赛 轰炸(bomb)
  • Callable接口
  • springboot整合redis实现秒杀功能
  • AI开发之——Leonardo—Finetuned Models及利用模型制图(5)
  • vue vben admin 使用, (个人感觉这项目封装的太深了!!!!)
  • 【故障诊断】用于轴承故障诊断的性能增强时变形态滤波方法及用于轴承断层特征提取的增强数学形态算子研究(Matlab代码实现)
  • JavaScript 基础 - 第3天
  • 刷题笔记【1】| 快速刷完67道剑指offer(Java版)
  • 四个常见的Linux面试问题
  • 2023年全国最新保安员精选真题及答案37
  • Qt 5基础 | 创建Hello World程序