使用 Java 编程判断排列交换

小红有一个长度为 n 的排列,她可以选择两个位置,然后交换两个位置的数。 她想知道能否通过最多一次交换,使得存在一个连续子段,是长度为 k 的排列。

排列是指一个长度为 len 的整数数组,数组中包含 1 到 len 的每个数,且每个数只出现一次。

输入描述 一行两个整数 n,k,表示排列长度和连续子段长度。一行 n 个整数 a1, a2, ..., an,表示排列。 1 ≤ k ≤ n ≤ 10^5

输出描述 如果能够通过最多一次交换,存在一个连续子段是排列,输出 YES,并输出交换的位置: 先输出一个整数 x (0 ≤ x ≤ 1),然后输出 x 行,每行两个整数 u,v,表示交换位置 uv。否则输出 NO。

思路:

  1. 首先判断原始排列是否已经是一个连续子段,如果是,则输出 YES 并且不需要交换位置;
  2. 如果不是连续子段,则遍历整个排列,找到第一个不在正确位置上的数,记为 num;
  3. 从 num 开始向后找连续子段,直到找到长度为 k 的连续子段或者遍历完整个排列;
  4. 如果找到了长度为 k 的连续子段,输出 YES,并输出交换的位置为 num 和子段的第一个数;
  5. 如果没有找到长度为 k 的连续子段,输出 NO。

代码实现如下:

import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        int k = sc.nextInt();
        int[] arr = new int[n];
        for (int i = 0; i < n; i++) {
            arr[i] = sc.nextInt();
        }
        sc.close();
        
        // 判断是否已经是连续子段
        boolean isConsecutive = true;
        for (int i = 0; i < n; i++) {
            if (arr[i] != i + 1) {
                isConsecutive = false;
                break;
            }
        }
        
        if (isConsecutive) {
            System.out.println("YES");
            System.out.println("0");
        } else {
            // 找到第一个不在正确位置上的数
            int num = 0;
            for (int i = 0; i < n; i++) {
                if (arr[i] != i + 1) {
                    num = arr[i];
                    break;
                }
            }
            
            // 从 num 开始找连续子段
            int start = 0;
            int end = 0;
            for (int i = 0; i < n; i++) {
                if (arr[i] == num) {
                    start = i;
                    end = i + 1;
                    while (end < n && arr[end] == arr[end - 1] + 1) {
                        end++;
                    }
                    break;
                }
            }
            
            // 判断是否找到了长度为 k 的连续子段
            if (end - start == k) {
                System.out.println("YES");
                System.out.println("1");
                System.out.println((start + 1) + " " + (end + 1));
            } else {
                System.out.println("NO");
            }
        }
    }
}
Java 编程实现排列交换判断

原文地址: https://www.cveoy.top/t/topic/mtP1 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录