Codeforces Round 899 (Div. 2)题解 A-C

14 篇文章 0 订阅
5 篇文章 0 订阅

A - Increasing Sequence

原题链接

题目描述
给你一个长度为n的数组a,要求你构造一个正整数数组b,并且满足 b i ≠ a i b_i \neq a_i bi=ai b 1 < b 2 < . . . < b n b_1 \lt b_2 \lt ... \lt b_n b1<b2<...<bn,求出 b n b_n bn的最小值。

思路:模拟+分类讨论

  • 如果 a 1 = 1 a_1 = 1 a1=1,那么 b 1 = a 1 + 1 b_1=a_1+1 b1=a1+1,否则 b 1 = 1 b_1=1 b1=1
public static void solve() throws IOException{
    int n = readInt();
    int[] a = utils.nextIntArray(n);
    int[] b = new int[n + 1];
    if (a[1] == 1) {
        b[1] = a[1] + 1;
    } else {
        b[1] = 1;
    }

    for (int i = 2; i <= n; i++) {
        if (b[i - 1] + 1 != a[i]) {
            b[i] = b[i - 1] + 1;
        } else {
            b[i] = a[i] + 1;
        }
    }
    printWriter.println(b[n]);
}

B - Sets and Union

原题链接

题目描述
给你n个集合 S 1 , S 2 , S 3 . . . S n S_1,S_2,S_3...S_n S1,S2,S3...Sn,你需要从中选中一些集合构成一个大集合 S S S,并且 S ≠ S 1 ∪ S 2 ∪ . . . ∪ S n S \neq S_1 \cup S_2 \cup ... \cup S_n S=S1S2...Sn,求这个大集合 S S S中元素最多可以是多少。

思路:思维+枚举

  • 数据范围较小,枚举删除每一种数时同时会带走最少其他种类的数的这个数即为答案。
public static void solve() throws IOException {
    int n = readInt();
    List<Integer>[] lists = new List[55];// 存下每个集合有多少种数
    List<Integer>[] nums = new List[55];// 存在每个数属于哪些集合
    Arrays.setAll(lists, g -> new ArrayList<>());
    Arrays.setAll(nums, g -> new ArrayList<>());
    Set<Integer> set = new HashSet<>();// 统计总共有多少种数
    int[] cnt = new int[55];// 统计每个数出现的次数
    for (int i = 1; i <= n; i++) {
        int m = readInt();
        for (int j = 1; j <= m; j++) {
            int p = readInt();
            lists[i].add(p);
            nums[p].add(i);
            set.add(p);
            cnt[p]++;
        }
    }
    int res = 0;
    for (int i = 1; i <= 50; i++) {
        if (set.contains(i)) {//这个数存在于集合当中
            int[] t = new int[55];// 临时存储删除 i时,每种数会被删除多少次
            for (int p : nums[i]) {// i所在集合
                for (int q : lists[p]) {// 集合 p所有元素 q
                    t[q]++;
                }
            }
            int cur = 0;
            for (int j = 1; j <= 50; j++) {
                if (t[j] != 0 && t[j] == cnt[j]) cur++;// 相等说明删除 i时 j同时会被完全删除
            }
            res = Math.max(res, set.size() - cur);
        }
    }

    printWriter.println(res);
}

C - Card Game

原题链接

题目描述
一副牌中有n张牌,每张牌上都带有一个分数 a i a_i ai,你的初始分数为0,现在你可以进行以下操作多次,以将你的分数最大化。

  • 选择一个奇数位置 i,将其删除并且将其分数叠加到你的分数上
  • 选择一个偶数位置 i,将其删除
  • 你可以随时结束游戏

思路:分类讨论+奇偶性+贪心

  • 1.第一个非负数(不是正整数)在奇数位,那么所有的正整数都可以取到(取当前奇数位或者删除偶数位的负数即可)
  • 2.第一个非负数(不是正整数)在偶数位,且不在第 2位上,那么可以通过删除前面的一个负数,让第一个非负数(不是正整数)处于奇数位
  • 3.第一个非负数(不是正整数)在偶数位,且在第 2位上,那么考虑保留第一个负数还是删除第二个非负数,取最大值即可
public static void solve() throws IOException {
    int n = readInt();
    int[] arr = new int[n + 1];
    long sum = 0;
    int p = -1;
    for (int i = 1; i <= n; i++) {
        arr[i] = readInt();
        if (arr[i] >= 0) {
            sum += arr[i];// 累加所有整数
            if (p == -1) p = i;// 记录第一个非负数的位置
        }
    }
    if (p == -1) {// 没有正数
        printWriter.println(0);
    } else if ((p & 1) == 1) {// 位于奇数位置
        printWriter.println(sum);
    } else {
        if (p == 2) {// 在第 2位上
            printWriter.println(Math.max(sum + arr[1], sum - arr[2]));
        } else {// 不在第 2位上
            printWriter.println(sum);
        }
    }
}
  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
抱歉,根据提供的引用内容,我无法理解你具体想要问什么问题。请提供更清晰明确的问题,我将竭诚为你解答。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* [Codeforces Round 860 (Div. 2)题解](https://blog.csdn.net/qq_60653991/article/details/129802687)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v92^chatsearchT0_1"}}] [.reference_item style="max-width: 33.333333333333336%"] - *2* [【CodeforcesCodeforces Round 865 (Div. 2) (补赛)](https://blog.csdn.net/t_mod/article/details/130104033)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v92^chatsearchT0_1"}}] [.reference_item style="max-width: 33.333333333333336%"] - *3* [Codeforces Round 872 (Div. 2)(前三道](https://blog.csdn.net/qq_68286180/article/details/130570952)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v92^chatsearchT0_1"}}] [.reference_item style="max-width: 33.333333333333336%"] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值