首页 > 编程语言 >【LGR-196-Div.4】洛谷入门赛 #26 题A - H 详细题解--优化思路简洁代码(C++,Python语言描述)

【LGR-196-Div.4】洛谷入门赛 #26 题A - H 详细题解--优化思路简洁代码(C++,Python语言描述)

时间:2024-08-19 22:26:42浏览次数:9  
标签:std 26 洛谷 int 题解 代码 cin C++ res

前言:

        觉得这个比赛很有意思的,都是暴力题,涉及一些细节,难度比较适合刚学编程语言的,可以很好的锻炼基础还有手速,最后两题也是比较有意思,之后也准备更新atc的比赛题解和洛谷的一些高质量比赛题解(算法网瘾就是想参加各种比赛)

      如果觉得有帮助,或者觉得我写的好,可以点个赞或关注,也可以看看我的一些其他文章,我之后也会更新一些基础算法详细解释

比赛链接:

【LGR-196-Div.4】洛谷入门赛 #26 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

目录

题A:

题目大意和解题思路:

代码(C++):

代码(Python):

题B:

题目大意和解题思路:

代码(C++):

代码(Python):

题C:

题目大意和解题思路:

代码(C++):

代码(Python):

题D:

题目大意和解题思路:

代码(C++):

代码(Python):

题E:

题目大意和解题思路:

代码(C++):

代码(Python):

题F:

题目大意和解题思路:

代码(C++):

代码(Python):

题G:

题目大意和解题思路:

代码(C++):

代码(Python):

题H:

题目大意和解题思路:

代码(C++):

代码(Python):


题A:

B4017 [语言月赛 202408] 相识于 2016 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

2018年8月是认识的第一个月,现在输入年和月,问认识了几个月

不需要管理月份大小的,只要月份小于8,那么表示肯定不是同一年

需要注意的是8月是第一个月,也就是7月是第0个月,减7就可以了

所以res = (x - 2016) * 12 + (y - 7) 

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int x, y;
    std::cin >> x >> y;
    int res = (x - 2016) * 12 + (y - 8) + 1;
    std::cout << res << std::endl;
}

代码(Python):

def main():
    x, y = map(int, input().split())
    res = (x - 2016) * 12 + (y - 7)
    print(res)

题B:

B4018 [语言月赛 202408] 游戏与共同语言 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

  • 胜局数者排名靠前
  • 若胜局数相同,净胜数者排名靠前
  • 若净胜数仍相同,平局记录者排名靠前
  • 不存在平局记录仍相同的情况

简单的判断就行,一个一个写就不会出错了

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int wa, ca, ta, wb, cb, tb;
    std::cin >> wa >> ca >> ta >> wb >> cb >> tb;
    bool f = 0;
    if (wa == wb) {
        if (ca == cb) {
            if (ta > tb) {
                f = 1;
            } else {
                f = 0;
            }
        } else if (ca > cb) {
            f = 1;
        } else {
            f = 0;
        }
    } else if (wa > wb) {
        f = 1;
    } else {
        f = 0;
    }
    if (f) {
        std::cout << "A" << std::endl;
    } else {
        std::cout << "B" << std::endl;
    }
}

代码(Python):

def main():
    wa, ca, ta = map(int, input().split())
    wb, cb, tb = map(int, input().split())
    f = 0
    if wa == wb:
        if ca == cb:
            if ta > tb:
                f = 1
            else:
                f = 0
        elif ca > cb:
            f = 1
        else:
            f = 0
    elif wa > wb:
        f = 1
    else:
        f = 0
    if f == 1:
        print("A")
    else:
        print("B")

题C:

B4019 [语言月赛 202408] 皆与生物有缘 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

本题就是求两名老师评分总分的平均值,向上取整

向上取整,加上除数减一就行了,这里的除数是2,那么就在总数上加一

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int n, x1 = 0, x2 = 0;
    std::cin >> n;
    int x;
    for (int i = 0; i < n; i++) {
        std::cin >> x;
        x1 += x;
    }
    for (int i = 0; i < n; i++) {
        std::cin >> x;
        x2 += x;
    }
    int res = (x1 + x2 + 1) / 2;
    std::cout << res << std::endl;
}

代码(Python):

def main():
    n = int(input())
    a1 = list(map(int, input().split()))
    a2 = list(map(int, input().split()))
    res = (sum(a1) + sum(a2) + 1) // 2
    print(res)

题D:

B4020 [语言月赛 202408] 两座城市的 543 千米 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

果一列高铁先经过 a,再经过 b,则称其为一列由 a 市直达 b 市的高铁

现在,给出所有高铁列车的信息,请问一共有多少列由 a 市直达 b 市的高铁

输入的第一行为四个整数 N,M,a,b。

接下来 M 行,每行的第一个整数为 l​,接下来输入 l 个数

保证同一次高铁不会重复停靠某座城市

这题的意思就是找一列数字中,是否先出现a,然后出现b,定义一个bool变量f然后遍历数组就行了,然后找到a,就把f变成1,继续遍历,当f == 1且找到b的时候,那么这个就是符合条件的

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int n, m, a, b;
    std::cin >> n >> m >> a >> b;
    int res = 0;
    for (int i = 0; i < m; i++) {
        int len;
        std::cin >> len;
        bool f = 0;
        for (int j = 0; j < len; j++) {
            int x;
            std::cin >> x;
            if (x == a) {
                f = 1;
            }
            if (f == 1 && x == b) {
                res += 1;
            }
        }
    }
    std::cout << res << std::endl;
}

代码(Python):

def main():
    n, m, a, b = map(int, input().split())
    res = 0
    for _ in range(m):
        arr = list(map(int, input().split()))
        f = 0
        for i in range(1, len(arr)):
            x = arr[i]
            if x == a:
                f = 1
            if f == 1 and x == b:
                res += 1
    print(res)

题E:

B4021 [语言月赛 202408] 于抑郁中支持 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

那是一段混沌的时期,风的记忆裂变为 n 块碎片,第 i 块的特征值为 ai。

定义整数 x 的后 p 位的值为 x mod 10^p。特征值后 t 位相同的记忆碎片,从属于同一事件。

请问,n 块碎片共从属于多少不同的事件

这题就是阅读理解吧,特征值后t位,那就是 x  mod 10 ^ t
把每一个数字x 的x mod 10 ^ t 求出来,然后看有哪些不同

可以把求出来的值放入一个set(),最后输出这个set的长度就行了

t <= 4 ,10 ^ 4也不需要用long long

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int n, t;
    std::cin >> n >> t;
    int mod = std::pow(10, t);
    std::unordered_set<int> has;
    for (int i = 0; i < n; i++) {
        int x;
        std::cin >> x;
        int a = x % mod;
        has.insert(a);
    }
    std::cout << has.size() << std::endl;
}

代码(Python):

def main():
    n, t = map(int, input().split())
    mod = 10 ** t
    arr = list(map(int, input().split()))
    has = set()
    for i in range(len(arr)):
        a = arr[i] % mod
        has.add(a)
    print(len(has))

题F:

B4022 [语言月赛 202408] 蓝色的网易云 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题目大意和解题思路:

风的歌单中共有 n 首歌,这些歌曲可以根据题材分为 m 类,第 i 首歌的题材为 ci​。风聆并不偏好任何一种题材,因此歌单中各题材的歌曲数量相同。

现在,请你给出一个歌曲播放顺序,使得相邻播放的歌曲题材不相同。

就是说数字表示这首歌的题材,现在需要一个播放的顺序,保证相邻的题材不同

然后歌单中各种题材的歌曲数量相同,这个条件很关键,如果没有这个条件那就是比较复杂的贪心了

歌单中各种题材的歌曲数量相同,那么对于每一种歌曲,取一首歌,排成一列,然后同样的方式把歌曲取完就行

比如题目中的示例:

1 1 2 2 3 3
先取1 2 3 排列, 然后再取1 2 3 ,最后的排列就是1 2 3 1 2 3

注意题目中输出的是歌曲的编号,而且是从1开始

可以定义一个m行的二维数组,每一行都表示一种歌曲题材

然后把歌曲存储进去,输出的时候就是每一列取一个数字输出即可

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int n, m;
    std::cin >> n >> m;
    std::vector<int> a(n);
    for (int i = 0; i < n; i++) {
        std::cin >> a[i];
    }
    std::vector<std::vector<int>> b(m, std::vector<int>());
    for (int i = 0; i < n; i++) {
        b[a[i] - 1].push_back(i + 1);
    }
    //遍历列,由于歌单中各种题材的歌曲数量相同,那么一个题材歌曲数量就是n / m
    for (int i = 0; i < n / m; i++) {
        //遍历行
        for (int j = 0; j < m; j++) {
            std::cout << b[j][i] << std::endl;
        }
    }
}

代码(Python):

def main():
    n, m = map(int, input().split())
    a = list(map(int, input().split()))
    b = [[] for _ in range(m)]
    for i in range(n):
        b[a[i] - 1].append(i + 1)
    for i in range(n // m):
        for j in range(m):
            print(b[j][i])

题G:

B4023 [语言月赛 202408] 因友情而终结 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

好恶心的字符串题目

题目大意和解题思路:

字符串 S 是一个仅由英文小写字母构成的串。现在,你可以对字符串 S 执行任意次如下操作:

  • 选择 S 长度为 4 的一个子串,将其替换为 love

请问,至少操作多少次,字符串 S 不再有子串 friend

定义:子串指的是一个字符串中连续的一段字符序列。例如,字符串 aabbcc 有子串 aabaabb,但 abc 不是字符串 aabbcc 的子串,因为其不连续。

开始我没想太多,觉得friend的数量就是答案

但其实不是,如果两个"friend"字符之间的距离小于3,那一个love就可以消除两个friend

从字符d开始替换成love即可

比如friendaafriend - > frienloveriend

我直接kmp

10^6的数据量,肯定不能直接替换的,可以先找出每个friend的起始位置,把位置放在一个数组中

然后遍历这个数组

看两个位置之间相差是否小于9,如果不小于9,那么这两个字符串就只需要一次操作就可以完成

具体看代码(有简单注释)

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    std::string s;
    std::cin >> s;
    //存放位置的数组
    std::vector<int> pos;
    std::string target = "friend";
    int p = s.find(target);
    //当找不到的时候跳出循环
    while (p != std::string::npos) {
        pos.push_back(p);
        //从此位置后6位再开始找
        p = s.find(target, p + 6);
    }
    int res = 0;
    //循环
    for (int i = 0; i < pos.size(); i++) {
        res++;
        //上一个位置
        int last = pos[i];
        //如果两个位置直接相差小于9,那么表示这两个friend可以一个love替换
        //然后i++,表示跳过下一个循环
        while (i + 1 < pos.size() && pos[i + 1] < last + 9) {
            i++;
        }
    }
    std::cout << res << std::endl;
}

代码(Python):

def main():
    s = input()
    #存放位置的数组
    pos = []
    target = "friend"
    p = s.find(target)
    #当找不到的时候跳出循环
    while p != -1:
        pos.append(p)
        #从此位置后6位再开始找
        p = s.find(target, p + 6)
    res, i = 0, 0
    while i < len(pos):
        res += 1
        #上一个位置
        last = pos[i]
        #如果两个位置直接相差小于9,那么表示这两个friend可以一个love替换
        #然后i++,表示跳过下一个循环
        while i + 1 < len(pos) and pos[i + 1] < last + 9:
            i += 1
        i += 1
    print(res)

题H:

B4024 [语言月赛 202408] 保持连接的方式 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

这题我说实话,就是烦人,没啥技巧,模拟就行了

题目大意和解题思路:

就是一个盒子,有m * n 个格子,每个格子最多只能放k个日记

然后每天写的日记放在某一格(从1开始计数)

如果这个格子满了,就取出最早放进去的日记销毁,然后输出此时销毁的日记编号和移动的日记数目

如果没满,就输出-1

比如示例:

输入

2 2 3 5
3 1 1
4 1 1
2 1 1
5 1 1
1 1 1

输出

-1
-1
-1
2 0
3 2

k为3,一个格子最多放3个,3进入(1, 1),4进入(1, 1), 2进入(1, 1)都不会满,输出-1

然后5进入满了,此时(1, 1)中编号最小的是2,需要移动0次,输出(2, 0)

1进入,移除3,需要移动2个
 

直接用一个哈希表模拟就行了

当哈希表此时的键对应的值小于k的时候,就输出-1

大于k的时候,就在里面找最小值的下标即可,输出下标

注意输入进来的x,y需要减一的操作

代码(C++):

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0);
    int n, m, k, t;
    std::cin >> n >> m >> k >> t;
    std::map<std::pair<int, int>, std::vector<int>> has;
    for (int i = 0; i < t; i++) {
        int a, x, y;
        std::cin >> a >> x >> y;
        x--; y--;
        auto key = std::make_pair(x, y);
        if (has[key].size() < k) {
            has[key].push_back(a);
            std::cout << -1 << std::endl;
        } else {
            int mn = *std::min_element(has[key].begin(), has[key].end());
            auto it = std::find(has[key].begin(), has[key].end(), mn);
            int move = has[key].size() - (it - has[key].begin()) - 1;
            has[key].erase(it);
            has[key].push_back(a);
            std::cout << mn << " " << move << std::endl;
        }
    }
    return 0;
}

代码(Python):

def main():
    n, m, k, t = map(int, input().split())
    has = defaultdict(list)

    res = []
    
    for _ in range(t):
        a, x, y = map(int, input().split())
        x -= 1
        y -= 1
        if len(has[(x, y)]) < k:
            has[(x, y)].append(a)
            res.append(-1)
        else:
            mn = min(has[(x, y)])
            i = has[(x, y)].index(mn)
            move = len(has[(x, y)]) - i - 1

            has[(x, y)].pop(i)
            has[(x, y)].append(a)
            res.append(f"{mn} {move}")
    print("\n".join(map(str, res)))

标签:std,26,洛谷,int,题解,代码,cin,C++,res
From: https://blog.csdn.net/2401_83669813/article/details/141275552

相关文章

  • [NOI]2024 登山 题解
    好像在洛谷题解区里还没人和我做法一样,,?考场做法,只用到了倍增和线段树,感觉挺好写。考场上从开题到过题只用了2h。最底下有省流版(?)。以下是我考场里比较详细的思路,所以比较长。先考虑如何\(O(n^2)\)做,然后再想优化。容易先想到一个状态数是\(O(n^2)\)的DP,即记录起点,并将向......
  • AGC002 题解
    目录A-RangeProductB-BoxandBallC-KnotPuzzleA-RangeProduct分情况讨论:\(a\le0\leb\)时,乘积一定为\(0\);否则:\(0<a\leb\)时,乘积一定为正;否则,负数的个数有\(b-a+1\)个,判断这个数是否为奇数,若是,乘积为负,否则为正。#include<bits/stdc++.h......
  • P10423题解
    P10423[蓝桥杯2024省B]填空问题先贴上答案#include<iostream>usingnamespacestd;intmain(){stringans[]={"1204","1100325199.77",};charT;cin>>T;cout<<ans[T-'A']......
  • P10155题解
    1题意给定一个排列ppp,每次可以选择一个数pi......
  • AT_abc027_b题解
    说明需要掌握贪心算法。这么简单为什么是黄题啊?题意给定一个长度为的非负整数序列,你可以进行若干次操作,每次操作都可以选择一个长度为的子串,花费的代价,将其中的每个数都变成该子串的平均值,现在你必须将每个数都变成相同的,你必须同时保证每个数为非负整数。分析先算......
  • 洛谷 P5731 蛇形方阵
    目录题目-蛇形方阵题目描述输入格式输出格式样例样例输入#1样例输出#1提示ACCODE思路ACCODE题目-蛇形方阵题目描述给出一个不大于9的正整数n,输出n×n的蛇形方阵。从左上角填上1开始,顺时针方向依次填入数字,如同样例所示。注意每个数字有都会占用3个字符,前面......
  • 题解:「ROI 2017 Day 2」存储器
    题目信息题目链接LuoguP10653、LOJ2770题目描述给定一个字符串\(S\),设其长度为\(n\),每个字符要么是+要么是-。定义一个片段为\(S\)的一个子串\(S[l,r]\)满足下面三个条件:\(l=1\)或者\(S_{l-1}\neS_l\)。\(r=n\)或者\(S_{r+1}\neS_r\)。\(S_l=S_{l+1}=......
  • P6218 [USACO06NOV] Round Numbers S 题解
    题面题目传送门如果一个正整数的二进制表示中,00的数目不小于11的数目,那么它就被称为「圆数」。例如,99的二进制表示为10011001,其中有22个00与22个11。因此,99是一个「圆数」。请你计算,区间[l,r][l,r]中有多少个「圆数」。前置芝士1.数位dp相关的题:P4317花神......
  • [题解]UVA1127 Word Puzzles
    UVA1127WordPuzzles我们对模式串建立AC自动机,然后就比较板子了,只需要把\(8\)个方向都跑一遍匹配就可以了。时间复杂度是\(O(T\times8nm)\)。注意输入是大写字母。点击查看代码#include<bits/stdc++.h>#defineK1010//模式串个数&矩阵长宽#defineN1000010//节点个......
  • el-table使用sortablejs推拽排序卡顿问题解决
    使用sortablejs拖拽el-table排序时,对于纯文本表格,正常使用即可,不会卡顿initSort(){consttbody=document.querySelector('.el-table__body-wrappertbody')const_this=thisSortable.create(tbody,{draggable:'.el-table__row',......