1 条题解

  • 0
    @ 2025-7-15 18:54:37

    方法思路

    1. 我们有n个珠子排成环形,其中3个是红色珠子,初始位置分别为a1、a2、a3
    2. 目标是通过相邻珠子交换,让任意两个红色珠子的最小距离不小于k
    3. 关键观察:
      • 如果3*k > n,则无解,因为环形上3个点的最大间距是n/3(平均分布)
      • 否则,我们可以通过移动珠子使它们之间的距离都不小于k
    4. 解决方案:
      • 首先将三个红珠子的位置排序
      • 计算相邻红珠子之间的距离:dist1 = red[1] - red[0], dist2 = red[2] - red[1], dist3 = n - red[2] + red[0](环形距离)
      • 如果任何距离小于k,则需要移动珠子使距离增加到k
      • 所需的最小交换次数就是所有需要增加的距离之和

    代码实现

    Java
    import java.util.*;
    
    public class Main {
        public static void main(String[] args) {
            Scanner sc = new Scanner(System.in);
            int t = sc.nextInt();
            
            for (int i = 0; i < t; i++) {
                long[] red = new long[3];
                long n = sc.nextLong();
                long k = sc.nextLong();
                red[0] = sc.nextLong();
                red[1] = sc.nextLong();
                red[2] = sc.nextLong();
                
                // 如果3*k > n,无解
                if (3 * k > n) {
                    System.out.println(-1);
                    continue;
                }
                
                // 对红珠子位置排序
                Arrays.sort(red);
                
                long res = 0;
                
                // 计算相邻红珠子之间的距离
                long dist1 = red[1] - red[0];
                if (dist1 < k) res += k - dist1;
                
                long dist2 = red[2] - red[1];
                if (dist2 < k) res += k - dist2;
                
                long dist3 = n - red[2] + red[0];  // 环形距离
                if (dist3 < k) res += k - dist3;
                
                System.out.println(res);
            }
        }
    }
    
    
    Python
    def min_swaps(n, k, a1, a2, a3):
        # 如果3*k > n,无解
        if 3 * k > n:
            return -1
        
        # 对红珠子位置排序
        red = [a1, a2, a3]
        red.sort()
        
        # 计算相邻红珠子之间的距离
        dist1 = red[1] - red[0]
        dist2 = red[2] - red[1]
        dist3 = n - red[2] + red[0]  # 环形距离
        
        # 计算需要增加的距离
        res = 0
        if dist1 < k:
            res += k - dist1
        if dist2 < k:
            res += k - dist2
        if dist3 < k:
            res += k - dist3
        
        return res
    
    # 处理输入
    t = int(input())
    for _ in range(t):
        n, k, a1, a2, a3 = map(int, input().split())
        print(min_swaps(n, k, a1, a2, a3))
    
    
    C++
    #include <iostream>
    #include <vector>
    #include <algorithm>
    using namespace std;
    
    int main() {
        int t;
        cin >> t;
        
        for (int i = 0; i < t; i++) {
            vector<long long> red(3);
            long long n, k;
            cin >> n >> k >> red[0] >> red[1] >> red[2];
            
            // 如果3*k > n,无解
            if (3 * k > n) {
                cout << -1 << endl;
                continue;
            }
            
            // 对红珠子位置排序
            sort(red.begin(), red.end());
            
            long long res = 0;
            
            // 计算相邻红珠子之间的距离
            long long dist1 = red[1] - red[0];
            if (dist1 < k) res += k - dist1;
            
            long long dist2 = red[2] - red[1];
            if (dist2 < k) res += k - dist2;
            
            long long dist3 = n - red[2] + red[0];  // 环形距离
            if (dist3 < k) res += k - dist3;
            
            cout << res << endl;
        }
        
        return 0;
    }
    
    
    • 1

    信息

    ID
    88
    时间
    1000ms
    内存
    256MiB
    难度
    5
    标签
    递交数
    1
    已通过
    1
    上传者