2023/05/02~07 刷题记录

news2024/10/7 12:25:54

A - AABCC

 题义:

 题解:

        读完题目可以想到直接暴力,但是肯定超时别想了。

        因为 a b c 都是素数,所以我们可以先求出所有的素数 进行减少循环的次数,然后遍历。在遍历过程中,我们也要去进行剪枝 ,如果说 a 的五次方大于了目标值,那后面肯定就都大于了,以此类推。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        long n = sc.nextLong();

        // 求素数 并放入集合中
        ArrayList<Integer> primeNumbers = new ArrayList<>(1000);
        getPrimeNumbers(n, primeNumbers);

        // 使用 HashSet 集合存储答案
        HashSet<Long> ans = new HashSet<>();
        long a, b, c, e;
        // 遍历所有可能 并使用if剪枝,如果说 a 的五次方大于了目标值,那后面肯定就都大于了
        for (int i = 0; i < primeNumbers.size(); i++) {
            a = primeNumbers.get(i);
            if (a * a * a * a * a > n)
                break;

            for (int j = i + 1; j < primeNumbers.size(); j++) {
                b = primeNumbers.get(j);
                if (a * a * b * b * b > n)
                    break;

                for (int k = j + 1; k < primeNumbers.size(); k++) {
                    c = primeNumbers.get(k);

                    e = a * a * b * c * c;
                    if (e <= n)
                        ans.add(e);
                    else
                        break;
                }
            }
        }

        // Set 集合中的个数 为答案的数量
        System.out.println(ans.size());
    }

    // 求素数,埃筛
    private static void getPrimeNumbers(long n, ArrayList<Integer> primeNumbers) {
        int len = (int) Math.sqrt(n) >> 1;

        // 初始化素数
        int[] temp = new int[len];
        temp[0] = 1;
        temp[1] = 1;

        for (int i = 2; i < len; i++) {
            if (temp[i] == 0) {
                for (int j = i * 2; j < len; j += i) {
                    temp[j] = 1;
                }

                primeNumbers.add(i);
            }
        }
    }
}

B - Same Map in the RPG World

题义:

 题解:
        我们还是可以第一眼想到暴力求解,但是这个暴力不能太直接了。

        我们可以把每一个点,当作是起点,然后根据这个点 去和 B 矩阵从(0, 0)开始比对。完全相同则为Yes。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int h = sc.nextInt();
        int w = sc.nextInt();
        sc.nextLine();

        // 存放数据矩阵
        char[][] a = new char[50][50];
        char[][] b = new char[50][50];
        for (int i = 0; i < h; i++)
            a[i] = sc.nextLine().toCharArray();
        for (int i = 0; i < h; i++)
            b[i] = sc.nextLine().toCharArray();

        // 先设为 false,遍历每一个点,把这些点当作为起点,然后和 B 矩阵对比
        boolean k = false;
        for (int i = 0; i < h; i++) {
            for (int j = 0; j < w; j++) {
                if (judge(a, b, i, j, h)) {
                    k = true;
                    break;
                }
            }
        }

        if (k)
            System.out.println("Yes");
        else
            System.out.println("No");
    }

    static boolean judge(char[][] a, char[][] b, int x, int y, int h) {
        int t = y;
        for (int i = 0; i < h; i++) {
            // 遍历 如果 x 大于了高度 h 则说明 A 矩阵已经从起点遍历到了最后 需要把 x+i 放到第一行
            x = x + i >= h ? x - h : x;
            y = t;
            for (int j = 0; j < a[i].length; j++) {
                // y 同理
                y = y + j >= a[i].length ? y - a[i].length : y;

                if (a[x + i][y + j] != b[i][j]) {
                    return false;
                }
            }
        }

        return true;
    }
}

 C - Cross

题义:

题解:

        遍历每一个点,把该点当作 X 图形的中心,求出这个点最大的 X 图形长度。既然是求最大,那么就不用考虑是否会交叉等问题。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        h = sc.nextInt();
        w = sc.nextInt();
        sc.nextLine();

        for (int i = 0; i < h; i++) 
            mp[i] = sc.nextLine().toCharArray();

        // 遍历每一个点当作中心
        for (int i = 0; i < h; i++)
            for (int j = 0; j < w; j++)
                if (mp[i][j] == '#')
                    fun(i, j);
                
        // 输出答案
        for (int i = 1; i <= Math.min(h, w); i++) 
            System.out.print(ans[i] + " ");
    }

    static int[] ans = new int[110];
    static char[][] mp = new char[110][100];
    static int h, w;

    // 求以(x, y)为中心,最大的 X 图像为多大
    static void fun(int x, int y) {
        int i = 1;
        while (true) {
            // 越界 就退出循环
            if (x - i < 0 || y - i < 0 || x + i >= h || y + i >= w)
                break;
            // 不能抵达 就退出循环
            if (mp[x - i][y - i] != '#' || mp[x + i][y - i] != '#' || mp[x - i][y + i] != '#' || mp[x + i][y + i] != '#')
                break;

            i++;
        }

        // 存进答案数组中
        ans[i - 1]++;
    }
}

D - Find by Query

题解:
        交互题。

        已知 s1 = 0,sn = 1。则不管中间是什么值,肯定会有一个分界的点,我们就是要求出这个点(任求一个)。很容易我们想到二分的方法,注意临界条件和判断条件。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int n = sc.nextInt();

        // 二分 每次询问中间的值,如果是 0,则往右边靠,因为最右边是 1。
        // 那肯定有一个分界点。如果是 1,同理。
        int l = 1, r = n, mid, res;
        while (l <= r) {
            mid = (l + r) / 2;
            System.out.println("?" + mid);
            res = sc.nextInt();
            if (res == 0)
                l = mid + 1;
            else
                r = mid - 1;
        }

        System.out.println("!" + r);
    }
}

E - Dango

题义:

题解:

        简单模拟题,注意细节就好了。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int n = sc.nextInt();
        sc.nextLine();

        String s = sc.nextLine();
        int ans = -1, l, r = -1;
        for (int i = 0; i < s.length(); i++) {
            // 如果该点为 -,则看是否为最大值 尝试存入答案
            if (s.charAt(i) == '-') {
                l = r;
                r = i;

                ans = Math.max(ans, r - l - 1);
            }
        }

        // 特殊情况,当 r == -1 则说明没有 -
        // 不为 r != -1 则求 从字符串最后到 倒数第一个 - 的距离 也可能为答案
        if (r != -1)
            ans = Math.max(ans, s.length() - r - 1);
        // 如果答案为 0,则没有 o,输出 -1
        if (ans == 0)
            ans--;
        System.out.println(ans);
    }
}

F - Cards Query Problem

题义:

题解:

        分别使用两个集合去存储数据。使用 ArrayList 集合当作一个盒子,把元素存进该集合中。

        使用 TreeSet 集合,存储对应下标卡片,在哪些盒子中存在。(其中 因为实现了 Set 接口 所以可以自动去重,又是 TreeSet 可以自动排序)

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int n = sc.nextInt();
        int q = sc.nextInt();
        int i, x;

        // 创建两个集合,分别存放一个盒子中有的卡片
        ArrayList<ArrayList<Integer>> arrayLists = new ArrayList<>(n);
        // 存放一个卡片的值 在哪些盒子中存在于 哪些盒子中,因为需要去重所以选择Set集合,又因为TreeSet自带排序
        ArrayList<TreeSet<Integer>> treeSets = new ArrayList<>(200010);
        for (i = 0; i < 200010; i++)
            treeSets.add(new TreeSet<>());
        for (i = 0; i < n; i++)
            arrayLists.add(new ArrayList<>(100));

        while (q-- != 0) {
            switch (sc.nextInt()) {
                case 1:
                    x = sc.nextInt();
                    i = sc.nextInt();

                    // 放入对应的集合
                    treeSets.get(x).add(i);
                    arrayLists.get(i - 1).add(x);
                    break;
                case 2:
                    i = sc.nextInt();

                    // 排序后输出 盒子中的全部卡片
                    ArrayList<Integer> integers = arrayLists.get(i - 1);
                    Collections.sort(integers);
                    for (Integer integer : integers)
                        System.out.print(integer + " ");
                    System.out.println();
                    break;
                case 3:
                    x = sc.nextInt();

                    // 输出对应卡片的集合里的 所有盒子(已经自动排序了)
                    TreeSet<Integer> treeSet = treeSets.get(x);
                    for (Integer integer : treeSet)
                        System.out.print(integer + " ");
                    System.out.println();
                    break;
            }
        }
    }
}

H - Writing a Numeral

 题义:

题解:

        全程使用一个 long 类型维护。

        操作一:加一个数后,进行对这个值取模。

        操作二:删除最前面的数,删除时考虑 当时的位数(队列的位数),而不是维护的数值的位数。因为维护的数会被取模。而在进行减的时候,也要先进行取模,否则可能会数字过大,这里还可以使用预处理进行减少计算的时间与次数。

        操作三:输出维护的这个数值。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        long n = sc.nextLong();

        // 需要 mod 的值
        final int INF = 998244353;
        // 初始化数值为 1,待会用来做乘法
        long ans = 1;
        // 预处理
        long[] div = new long[600005];
        div[0] = 1;
        for (int i = 1; i < 600005; i++)
            div[i] = div[i - 1] * 10 % INF;

        // 使用 LinkedList 集合来存储各个位上的数字,方便尾插和弹出队头
        LinkedList<Integer> linkedList = new LinkedList<>();
        linkedList.add(1);
        for (long i = 0; i < n; i++) {
            switch (sc.nextInt()) {
                case 1:
                    // 插入队尾
                    int a = sc.nextInt();
                    linkedList.addLast(a);
                    ans = ans * 10 + a;
                    ans = myMod(ans, INF);
                    break;
                case 2:
                    // 移除头节点,并将维护的数字减去这个头节点对应的值
                    Integer first = linkedList.removeFirst();
                    ans -= (long) first * div[linkedList.size()];
                    // 减去之后可能为负数,改为自己定义的 mod 方法
                    ans = myMod(ans, INF);
                    break;
                case 3:
                    // 输出维护的数值
                    System.out.println(ans);
                    break;
            }
        }
    }

    // mod 可能为负数,自定义 mod
    static long myMod(long x, long mod) {
        x %= mod;
        while (x < 0)
            x += mod;
        return x;
    }
}

 J - M<=ab

 题义:

 题解:

        阅读完题目很容易想到暴力,也就是从 M 开始,一个一个试看是否有两个数字可以相乘的值为它,并且这两个值都小于 N。但是肯定超时。。。

        改变思路,我们可以从 1 开始 (设为 i),求出一个与 i 相乘 大于等于 M 且最接近 M 的值。推导出 

(m + i - 1) / i;

        为什么要 +i ?因为 M / i * i 的值可能会小于 M,加了 i 之后,计算出来的结果一定会使得 求出来的值 乘以 i 大于等于 M。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        long n = sc.nextLong();
        long m = sc.nextLong();
        long k, ans = Long.MAX_VALUE;

        for (long i = 1; i <= n; i++) {
            // 求出一个 与 i 相乘 大于等于 M 的值,且该值为最接近 M 的
            k = (m + i - 1) / i;

            // 剪枝,如果 i 大于了 k 的话,其实后面的值 之前都遍历过了,break 跳出
            if (i <= k) {
                // 如果 k 在答案的范围内(1-n),则对比一下结果
                if (k <= n)
                    ans = Math.min(ans, i * k);
            } else {
                break;
            }
        }

        if (ans == Long.MAX_VALUE)
            System.out.println(-1);
        else
            System.out.println(ans);
    }
}

K - Gap Existence

 题义:

 题解:

        使用 HashSet 进行存储数据(包含了去重、快速查找功能)。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int n = sc.nextInt();
        int x = sc.nextInt();

        // 使用 HashSet 存储,满足题目的快速查找(hash值)和去重剪枝需求
        HashSet<Integer> hashSet = new HashSet<>(n);
        for (long i = 0; i < n; i++)
            hashSet.add(sc.nextInt());

        // 判断是否含有这个值,a - x 的值
        boolean k = false;
        for (Integer a : hashSet) {
            if (hashSet.contains(a - x)) {
                k = true;
                break;
            }
        }

        if (k)
            System.out.println("Yes");
        else
            System.out.println("No");
    }
}

L - 2xN Grid

题义:

题解:
        简单模拟题。

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        long len = sc.nextLong();
        long n1 = sc.nextLong();
        long n2 = sc.nextLong();

        ArrayList<Node> nodes = new ArrayList<>();
        for (int i = 0; i < n1; i++)
            nodes.add(new Node(sc.nextLong(), sc.nextLong()));

        int now = 0;
        long ans = 0, x = 0, l = 0, xx = 0, ll = 0;
        for (int i = 0; i < n2; i++) {
            x = sc.nextLong();
            l = sc.nextLong();

            // 将 B 序列的值 循环消耗完
            while (l != 0) {
                if (ll == 0) {
                    Node node = nodes.get(now++);
                    xx = node.x;
                    ll = node.l;
                }

                if (l <= ll) {
                    if (x == xx)
                        ans += l;
                    ll -= l;
                    l = 0;
                } else {
                    if (x == xx)
                        ans += ll;
                    l -= ll;
                    ll = 0;
                }
            }
        }

        System.out.println(ans);
    }

    static class Node {
        long x, l;

        Node(long x, long l) {
            this.x = x;
            this.l = l;
        }
    }
}

M - Bank

题义:

题解:

        该题目对 Java 选手不太友好,这样都超时。

        因为,题目只有操作二可以删除元素,而在删除之前肯定会添加该元素,所以操作一都不用管。操作三时,如果 bool 值为 true 则说明该值已经被删除了,则 ++ 判断下一个值。

import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        int n = sc.nextInt();
        int q = sc.nextInt();

        // 创建一个 bool 数组判断是否删除了该元素
        boolean[] booleans = new boolean[n+1];
        int last = 1;

        for (int i = 0; i < q; i++) {
            switch (sc.nextInt()) {
                case 2:
                    // 操作二 删除一个元素
                    int a = sc.nextInt();
                    booleans[a] = true;
                    break;
                case 3:
                    // 操作三 输出一个最小的没有被删除的元素
                    while (booleans[last])
                        last ++;
                    System.out.println(last);
                    break;
            }
        }
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/499404.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

10_Uboot启动流程_2

目录 _main函数详解 board_init_f函数详解 relocate_code函数详解 relocate_vectors函数详解 board_init_r 函数详解 _main函数详解 在上一章得知会执行_main函数_main函数定义在文件arch/arm/lib/crt0.S 中,函数内容如下: 第76行,设置sp指针为CONFIG_SYS_INIT_SP_ADDR,也…

美团外卖红包优惠券:美团外卖节红包或美团外卖天天神券怎么领取使用?

什么是美团外卖节红包或美团外卖天天神券&#xff1f; 美团外卖节红包、美团外卖天天神券都可以称为美团外卖红包优惠券。使用美团外卖节红包、美团外卖天天神券&#xff0c;点餐可以享受优惠。且美团外卖节红包、美团外卖天天神券每天都可以免费领取。美团会员红包不能与美团…

nginx相关知识

目录 一. Nginx目录结构 二. Nginx配置文件结构 三. Nginx具体应用 1. 部署静态资源 2. 反向代理 3. 负载均衡 一. Nginx目录结构 重点目录/文件&#xff1a; conf/nginx.conf nginx配置文件html 存放静态文件&#xff08;html、CSS、Js等&#xff09;logs 日志目…

【Redis】数据结构底层结构

我们知道Redis的很快&#xff0c;一个原因是因为在内存上操作&#xff0c;另一个原因是本身的数据结构。而具体的五大类型就是如下&#xff1a; 键和值如何组织的 通过key找到value的过程&#xff0c;Redis使用了哈希表结构进行查找。具体就是根据key的hash值计算出对应的下…

三子棋(C语言重做版)

&#x1f929;本文作者&#xff1a;大家好&#xff0c;我是paperjie&#xff0c;感谢你阅读本文&#xff0c;欢迎一建三连哦。 &#x1f970;内容专栏&#xff1a;这里是《C语言》专栏&#xff0c;笔者用重金(时间和精力)打造&#xff0c;基础知识一网打尽&#xff0c;希望可以…

对标ChatGPT3.5,支持手机电脑网页使用,无需魔法

说到 Claude 是什么&#xff0c;大家可能没听说过。 但是说到 OpenAI&#xff0c;说到 ChatGPT&#xff0c;相信大家一定听说过&#xff0c;玩过。 PS&#xff1a;关于 Claude 网页版的注册教程&#xff0c;我之前已经写过文章了&#xff0c;现在额外介绍如何使用手机App和电脑…

centos搭建code-server及配置HTTPS、登录页自定义

文章目录 一、Code-Server二、安装及运行三、系统配置四、HTTPS配置五、登录页面自定义 注&#xff1a;本版本基于4.11.0&#xff0c;在此之前版本&#xff0c;在centos上会出现CPU占用一直100%的情况&#xff0c;当前版本已经搭建两个月&#xff0c;综合下来比较稳定 通过搭建…

【高数+复变函数】傅里叶级数

文章目录 1. 傅里叶级数1.1 和差化积积化和差1.2 三角函数系的正交性1.3 系数公式求解1.4 展开条件1.5 变形下的傅里叶 在课程学习中&#xff0c;感觉这一部分的东西频繁会被用到&#xff0c;因此写下来做个总结。 1. 傅里叶级数 在科学技术中&#xff0c;常常会遇到各种各样的…

【matplotlib】4-完善统计图形

文章目录 完善统计图形1 添加图例和标题1.1 图例和标题的设置方法1.2 案例1--图例的展示样式的调整1.3 案例2--标题的展示样式的调整1.4 案例3--带图例的饼图 2 调整刻度范围和刻度标签2.1 调整刻度范围和刻度标签的方法2.2 子区函数--subplot()2.3 案例--逆序设置坐标轴刻度标…

密码学:公钥密码.(非对称密码)

密码学&#xff1a;公钥密码. 公钥密码 (Public Key Cryptography)&#xff0c;又称为非对称密码&#xff0c;其最大特征是加密和解密不再使用相同的密钥&#xff0c;而使用不同的密钥。使用者会将一个密钥公开&#xff0c;而将另一个密钥私人持有&#xff0c;这时这两个密钥被…

【WebGIS初学到入职】第二阶段的小结

一、前言 2021年12月&#xff0c;我进行了【WebGIS初学到入职】第一阶段的小结&#xff0c;如今&#xff0c;一年半过去了。我完成了毕业设计&#xff0c;平缓得通过了岗位的试用期&#xff0c;而且作为我所在部门唯一的前端开发&#xff0c;参与了越来越多的工作项目。 同时…

源码分析RocketMQ之NameServer

整体架构图 从部署架构图可知NameServer与所有的broker通讯&#xff0c;NameServer集群之间互不通信。 主要功能包括 1、Broker管理 1.1 维护Broker集群 clusterAddrTable 1.2 Broker信息 接收Broker注册信息并保存作为路由信息的基本数据 brokerAddrTable 1.3 Topic消息路由…

【软件质量保证与测试】实验二之ACTS工具

索引 0. 前言1. ACTS 获取2. ACTS 启动2.1 双击启动GUI2.2 终端启动GUI2.3 进入GUI 3. ACTS 参数类型3.1 新建系统3.2 ACTS 添加成员3.2.1 Boolean类型3.2.2 Enum类型3.2.3 Number类型3.2.4 Range类型3.2.5 其他 4. ACTS 约束5. 混合组合强度6. 参考模型6.1 设定模型6.2 参数设…

Win系统软件闪屏 - 解决方案

Win系统软件闪屏 - 解决方案 前言原因解决方案方法1&#xff1a;软件使用独显方法2&#xff1a;软件关闭硬件加速方法3&#xff1a;降级显卡驱动 前言 使用Win10及以上系统时&#xff0c;可能会出现频繁闪现黑屏的状态&#xff0c;下文简称闪屏。一般在使用第三方软件时&#…

【Linux】进程信号保存

前言 上篇博客我们了解了进程信号的概念和信号如何产生。 本篇我们将学习进程信号如何保存。 文章目录 前言一. 阻塞信号二. 递达动作三. 信号集四. 信号集操作函数结束语 一. 阻塞信号 首先我们需要一些预备知识 实际执行信号的处理动作称为信号递达&#xff08;Delivery&am…

可能是最有前途的国产大模型:讯飞星火认知大模型

大家好&#xff0c;我是可夫小子&#xff0c;关注AIGC、读书和自媒体。解锁更多ChatGPT、AI绘画玩法。加&#xff1a;keeepdance&#xff0c;备注&#xff1a;chatgpt&#xff0c;拉你进群。 昨天下午&#xff0c;科大讯飞发布了自己的大模型——星火认知大模型。在上周他们还在…

小白专用VScode从安装到入门编写_Windows_C/C++

此篇主要梳理VScode的安装、功能拓展等&#xff0c;包括与git管理和Cmake的结合 一、VScode下载二、VScode功能拓展2.1 VScode中文界面在线安装2.2 VScode中文界面离线安装2.3 鼠标滚轮调整字体大小2.4 调整编辑器界面大小2.5 Windows下VScode C/C环境配置2.5.1 MinGW编译器下载…

Illustrator如何创建Web图形与动画之实例演示?

文章目录 0.引言1.创建切片2.选择和编辑切片3.快速生成PNG元素图标 0.引言 因科研等多场景需要进行绘图处理&#xff0c;笔者对Illustrator进行了学习&#xff0c;本文通过《Illustrator CC2018基础与实战》及其配套素材结合网上相关资料进行学习笔记总结&#xff0c;本文对创建…

【Docker】docker核心概念与常用指令

目前掌握的docker处理平时工作倒是可以&#xff0c;但docker网络这块有些模棱两可&#xff0c;干脆从头整理一遍Docker。 &#x1f333;&#x1f333;【Docer篇整理】&#x1f333;&#x1f333; 篇一&#xff1a;docker核心概念与常用指令 篇二&#xff1a;镜像与docker数据卷…

【C++】vector的介绍及使用

目录 一、vector的介绍二、vector的常用接口2.1 vector的定义2.2 vector iterator的使用2.3 vector 空间增长问题2.4 vector 增删查改2.4.1.尾插和尾删2.4.2.任意位置插入和删除以及查找2.4.3.vector 的交换与遍历 2.5 vector 迭代器失效问题 一、vector的介绍 vector是表示可…