AtCoder Regular Contest 159

news2024/11/27 10:21:30

B - GCD Subtraction

题意:

给定两个正整数 A , B A,B A,B,给定一个操作:令 g = g c d ( A , B ) g=gcd(A, B) g=gcd(A,B),令 A = A − g , B = B − g A=A-g, B=B-g A=Ag,B=Bg。问最少经过多少次操作之后其中一个数变为0.

思路:

A ′ = A / g , B ′ = B / g A'=A/g,B'=B/g A=A/g,B=B/g,操作一次后等价于求 ( A ′ − 1 ) ∗ g , ( B ′ − 1 ) ∗ g (A'-1)*g,(B'-1)*g (A1)g,(B1)g的答案。而且不难发现的是,后面的 g g g对答案并无影响,所以等价于求 A ′ − 1 , B ′ − 1 A'-1,B'-1 A1,B1的答案。
显然,如果 g > 1 g>1 g>1那么该操作最多进行 l o g log log次,直接暴力递归求解即可。如果 g = 1 g=1 g=1,那么我们需要找到一个最小的整数 x x x,使得 g c d ( A ′ − 1 − x , B − 1 − x ) ≠ 1 gcd(A'-1-x,B-1-x)\neq1 gcd(A1x,B1x)=1。即满足 A ≡ B ( m o d m ) A\equiv B(mod m) AB(modm)。我们令 A = k 1 ∗ m + b 1 , B = k 2 ∗ m + b 1 A=k_1*m+b_1,B=k_2*m+b_1 A=k1m+b1,B=k2m+b1,我们要找最小的 b 1 b_1 b1 A − B A-B AB也是 m m m的倍数,那么我们暴力枚举 A − B A-B AB的因数即可。时间复杂度 n ∗ l o g n \sqrt{n}*logn n logn

代码:


LL a, b, ans;
 
void solve(LL x) {
    LL t = b;
    for(LL i = 2; i * i <= x; i++) {
        if(x % i == 0) {
            if(a % i == b % i) t = min(t, a % i);
            if(a % (x / i) == b % (x / i)) t = min(t, a % (x / i));
        }
    }
    if(a % x == b % x) t = min(t, a % x);
    ans += t;
    a -= t;
    b -= t;
}
 
int main() {
	ios::sync_with_stdio(false);
	cin.tie(nullptr);
 
    cin >> a >> b;
    while(a && b) {
        if(a < b) swap(a, b);
        LL g = __gcd(a, b);
        a /= g, b /= g;
        a--, b--;
        ans++;
        if(a == 0 || b == 0) break;
 
        if(a - 1 == b) {
            ans += b;
            break;
        }
        if(a == b) {
            ans++;
            break;
        }
        solve(a - b);
    }
    cout << ans << '\n';
 
	return 0;
}

C - Permutation Addition

题意:

给定一个长为 n , n ≤ 50 n,n\leq 50 nn50的数组 a [ i ] a[i] a[i],每次可以选择一个 n n n的排列 p p p,使得 a [ i ] = a [ i ] + p [ i ] a[i]=a[i]+p[i] a[i]=a[i]+p[i],求能否在操作次数不超过 1 e 4 1e4 1e4的前提下将数组所有元素变得相等。

思路:

对于这种限制操作次数,而且很明显操作次数会很多的构造题,我们应尽量去找存不存在一个元操作使数组有某种变化,然后复制该操作。
我们令 s u m = ∑ a [ i ] sum=\sum{a[i]} sum=a[i],显然最后要使 s u m % n = 0 sum\%n=0 sum%n=0
n n n为奇数,则 n ∗ ( n + 1 ) 2 % n = 0 \frac{n*(n+1)}{2}\%n=0 2n(n+1)%n=0 s u m % n = 0 sum\%n=0 sum%n=0有解,我们构造两个排列: n = 5 n=5 n=5
p : 1 2 3 4 , p ′ : 4 3 2 1 p:1\quad 2 \quad 3 \quad 4, p':4\quad 3\quad 2\quad 1 p:1234,p:4321。之后相当于 a [ 1 ] + 1 , a [ 2 ] − 1 a[1]+1,a[2]-1 a[1]+1,a[2]1。那么我们就找到了一个元操作,使得一个位置增加1,一个位置减少1.
n n n为偶数,则 n ∗ ( n + 1 ) 2 % n = n 2 \frac{n*(n+1)}{2}\%n=\frac{n}{2} 2n(n+1)%n=2n,则 s u m % n = 0 , s u m % n = n 2 sum\%n=0,sum\%n=\frac{n}{2} sum%n=0sum%n=2n有解。
对于 s u m % n = n / 2 sum\%n=n/2 sum%n=n/2,我们先随便找一个排列将其变成 s u m % n = 0 sum\%n=0 sum%n=0即可。

代码:

int main() {
	ios::sync_with_stdio(false);
	cin.tie(nullptr);
 
    int n;
    cin >> n;
    vector<int> a(n + 1);
    int sum = 0;
    for(int i = 1; i <= n; i++) {
        cin >> a[i];
        sum += a[i];
    }
    if(n % 2 == 0 && sum % n != 0 && sum % n != n / 2) {
        cout << "No\n";
        return 0;
    }
    if(n % 2 && sum % n != 0) {
        cout << "No\n";
        return 0;
    }
    cout << "Yes\n";
    int f = 0;
    if(n % 2 == 0 && sum % n == n / 2) {
        f = 1;
        sum += n * (n + 1) / 2;
        for(int i = 1; i <= n; i++) a[i] += i;
    }   
    vector<int> x, y;
    int mid = sum / n;
    for(int i = 1; i <= n; i++) {
        while(a[i] < mid) x.pb(i), a[i]++;
        while(a[i] > mid) y.pb(i), a[i]--;
    }
    cout << SZ(x) * 2 + f << '\n';
    if(f) {
        for(int i = 1; i <= n; i++) cout << i << " \n"[i == n];
    }
    for(int i = 0; i < SZ(x); i++) {
        int l = 2, r = n - 1;
        for(int j = 1; j <= n; j++) {
            cout << (j != x[i] && j != y[i] ? ++l : (j == x[i] ? 2 : 1)) << " \n"[j == n];
        }
        for(int j = 1; j <= n; j++) {
            cout << (j != x[i] && j != y[i] ? --r : (j == x[i] ? n : n - 1)) << " \n"[j == n];            
        }
    }
    
 
	return 0;
}

D - LIS 2

题意:

在这里插入图片描述

思路:

一个很重要的性质:若一个区间被选,那么选的一定是其一个后缀。
所以我们定义 d p [ i ] dp[i] dp[i]:第i个区间必选的最长上升子序列。
转移:
若区间 j , r [ j ] < l [ i ] j,r[j]<l[i] j,r[j]<l[i],那么 f [ i ] = m a x ( f [ j ] + r [ i ] − l [ i ] + 1 ) f[i]=max(f[j]+r[i]-l[i]+1) f[i]=max(f[j]+r[i]l[i]+1)
若区间 j , r [ j ] ≥ l [ i ] j,r[j]\geq l[i] j,r[j]l[i],那么 f [ i ] = m a x ( f [ j ] + r [ i ] − r [ j ] ) f[i]=max(f[j]+r[i]-r[j]) f[i]=max(f[j]+r[i]r[j])
那么我们将其离散化后建两颗线段树分别维护 f [ j ] , f [ j ] − r [ j ] f[j],f[j]-r[j] f[j],f[j]r[j]即可。

代码:

#define int LL
int lsh[N], a[N], n;
int l[N], r[N];
int ll[N], rr[N];
 
struct Node {
    int tr[N * 4];
    void pushup(int u) {
        tr[u] = max(tr[lson], tr[rson]);
    }
    void modify(int u, int l, int r, int pos, int val) {
        if(l == r && l == pos) {
            tr[u] = max(tr[u], val);
            return;
        }
        int mid = l + r >> 1;
        if(pos <= mid) modify(lson, l, mid, pos, val);
        else modify(rson, mid + 1, r, pos, val);
        pushup(u);
    }
    int query(int u, int l, int r, int L, int R) {
        // return 0;
        // cout << u << ' ';
        if(L <= l && r <= R) {
            return tr[u];
        }
        int mid = l + r >> 1;
        int res = -INF;
        if(L <= mid) res = max(res, query(lson, l, mid, L, R));
        if(R > mid) res = max(res, query(rson, mid + 1, r, L, R));
        return res;
    }
}seg1, seg2;
int dp[N];
 
signed main() {
	ios::sync_with_stdio(false);
	cin.tie(nullptr);
 
    memset(seg1.tr, -0x3f, sizeof seg1.tr);
    memset(seg2.tr, -0x3f, sizeof seg2.tr);
    cin >> n;
    int id = 0;
    for(int i = 1; i <= n; i++) {
        cin >> l[i] >> r[i];
        lsh[++id] = l[i],
        lsh[++id] = r[i];
    }
    sort(lsh + 1, lsh + 1 + id);
    id = unique(lsh + 1, lsh + 1 + id) - lsh - 1;
    for(int i = 1; i <= n; i++) {
        ll[i] = lower_bound(lsh + 1, lsh + 1 + id, l[i]) - lsh;
        rr[i] = lower_bound(lsh + 1, lsh + 1 + id, r[i]) - lsh;
        // DD(ll[i], rr[i])
    }
    dp[0] = 0;
    seg1.modify(1, 0, 2 * n, 0, 0);
    seg2.modify(1, 0, 2 * n, 0, 0);
    for(int i = 1; i <= n; i++) {
        dp[i] = max(dp[i], seg1.query(1, 0, 2 * n, 0, ll[i] - 1) + r[i] - l[i] + 1);
        dp[i] = max(dp[i], seg2.query(1, 0, 2 * n, ll[i], rr[i]) + r[i]);
        // D(dp[i])
        // DD(seg2.tr[5], seg2.tr[6])
        seg1.modify(1, 0, n * 2, rr[i], dp[i]);
        seg2.modify(1, 0, n * 2, rr[i], dp[i] - r[i]);
    }
    LL ans = *max_element(dp + 1, dp + 1 + n);
    cout << ans;
 
	return 0;
}

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

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

相关文章

APPScan介绍以及安装方式【附带链接】

AppScan介绍和安装 请务必下载绑定的链接&#xff0c;避免环境错误 1.简介 Appscan 10中文版是是全新网络安全漏洞扫描软件&#xff0c;软件可以直接可以对OS命令、SSRF和XXE攻击等漏洞进行检测&#xff0c;使得漏洞检测更加容易&#xff0c;提高漏洞的扫描效率。软件同时支…

[LeetCode周赛复盘] 第 354 场周赛20230716

[LeetCode周赛复盘] 第 354 场周赛20230716 一、本周周赛总结6889. 特殊元素平方和1. 题目描述2. 思路分析3. 代码实现 6929. 数组的最大美丽值1. 题目描述2. 思路分析3. 代码实现 6927. 合法分割的最小下标1. 题目描述2. 思路分析3. 代码实现 6924. 最长合法子字符串的长度1.…

Go语言之重要数组类型map(映射)类型

通过切片&#xff0c;我们可以动态灵活存储管理学生姓名、年龄等信息&#xff0c;比如 names : []string{"张三","李四","王五"} ages : []int{23,24,25} fmt.Println(names) fmt.Println(ages)但是如果我想获取张三的年龄&#xff0c;这是一个…

概率论的学习和整理17:EXCEL的各种期望,方差的公式

目录 1 总结 1.1 本文目标总结方法 1.2 总结一些中间关键函数 2 均值和期望 2.1 求均值的公式 2.2 求随机变量期望的公式 2.3 求随机变量期望的朴素公式 3 方差 3.1 确定数的方差 3.2 统计数的方差公式 3.3 随机变量的方差公式 3.4 EXCEL提供的直接计算方差的公式 …

Ant Design Vue组件,a-select标签

a-select标签是组件里的选择框&#xff0c;具体使用可以查看官网&#xff0c;这里记录一下在使用中遇到的问题。 最近在做项目的时候有一个需求在 a-modal 标签中加入 a-select 标签&#xff0c;a-modal 是模态对话框&#xff0c;意思就是在模态对话框里面添加选择框&#xff0…

Cglib 动态代理实现

每天看看新东西,心情也要好上许多 问题 cglib是如何实现动态代理的cglib如何支持类的代理cglib和jdk的动态代理有什么区别 使用方式 cglib不属于jdk的一部分,因此要使用需要先引入相应的包,maven依赖如下 <dependency><groupId>cglib</groupId><artif…

TortoiseGit 入门指南09:合并

前面章节讲了 分支&#xff0c;提到一种常用的工作流&#xff1a;将默认分支&#xff08;master&#xff09;设置为主分支&#xff0c;保存最新的、随时可以发布的版本&#xff0c;所有的新特性、BUG都在另一个称为特性分支上增加或修改&#xff0c;然后在一个合适点&#xff0…

Ubuntu下搭建Redis主从集群

目录 准备实例和配置 开启主从关系 测试配置 搭建的主从集群结构&#xff0c;只有主服务器与客户端进行写操作&#xff0c;通过主从同步数据&#xff0c;从服务器向客户端提供读操作 共包含三个节点&#xff0c;一个主节点&#xff0c;两个从节点。 这里我们会在同一台虚拟机…

【C++】多线程编程二(std::thread详解)

目录 std::thread详解 &#xff08;1&#xff09;启动线程 ①无参无返回的函数作为入参 ②函数对象&#xff08;仿函数&#xff09;作为入参 &#xff08;2&#xff09;不等待线程detch() &#xff08;3&#xff09;等待线程完成join() &#xff08;4&#xff09;向线程…

CANoe如何配置Master/Slave模式

系列文章目录 文章目录 系列文章目录前言一、CANoe配置端口二、CANoe配置Master模式三、CANoe配置Slave模式前言 随着智能电动汽车的行业的发展,车载以太网的应用越来越广泛,最近很多朋友在问CANoe Master/Slave模式如何设置,车载以太网物理层也有一项是测试Master/Slave模式…

springcloud整合nacos实现注册发现中心

文章目录 微服务为什么需要服务注册发现中心怎么使用注册发现中心1.本示例环境2.nacos 安装3.pom.xml4.application.yml5.NacosDiscoveryDemoController6.ServerConfig7.NacosNacosDiscoveryServiceImpl8.启动用http工具测试结果 如果需要完整源码请关注公众号"架构殿堂&q…

2023.7.16-偶数(奇数)的枚举

功能&#xff1a;输入一个整数&#xff0c;结果打印出所有不大于这个整数的偶数。 程序&#xff1a; #define _CRT_SECURE_NO_WARNINGS 1 #include<stdio.h> int main() {int a, b;printf("请输入一个整数&#xff1a;");scanf("%d",&a);print…

Android之Intent

意图介绍 一个意图(Intent)对象包含了目标组件、动作、数据、类别、附加数据、标志六个部分。 目标组件 目标组件可以帮助应用发送显式意图调用请求。在创建Intent时&#xff0c;可以通过setComponent方法来设置一个组件&#xff0c;如&#xff1a; //设置组件 intent.setC…

19.基于XML的自动装配

基于XML的自动装配 自动装配&#xff1a; 根据指定的策略&#xff0c;在IOC容器中匹配某一个bean&#xff0c;自动为指定的bean中所依赖的类类型或接口类型属性赋值 使用bean标签的autowire属性设置自动装配效果(默认为no和defalse不进行装配——bean中的属性不会自动匹配某个b…

Nodejs的字节操作(Buffer)

Hi I’m Shendi Nodejs的字节操作&#xff08;Buffer&#xff09; 字节操作是一个编程语言中必不可少的&#xff0c;而在NodeJs中也可以很方便的进行字节操作。 Buffer类 在 js 中没有二进制数据类型&#xff0c;但在一些情况下必须使用到二进制数据类型&#xff0c;比如网络通…

ModaHub魔搭社区:AI原生云向量数据库Zilliz Cloud与 OpenAI 集成搭建相似性搜索系统

目录 准备工作 检索图书 本文将讨论如何使用 OpenAI 的 Embedding API 与 Zilliz Cloud 搭建相似性搜索系统。 在本篇中你将看到如何使用 OpenAI 的 Embedding API 和 Zilliz Cloud 完成图书检索。当前,很多的图书检索方案,包括公共图书馆里使用的那些方案,都是使用关键词…

简单认识MySQL数据库事务

文章目录 一、MySQL事务的概念1、简介2、事务的ACID特点1.原子性&#xff08;Atomicity&#xff09;2.一致性&#xff08;Consistency&#xff09;3.隔离性&#xff08;lsolation&#xff09;4.持久性&#xff08;Durability) 3、并发访问表的一致性问题和事务的隔离级别1.并发…

C# Modbus通信从入门到精通(6)——Modbus RTU(0x04功能码)

1、04(0x04)读输入寄存器 使用该功能码能从远程地址中读取1到125个输入寄存器的值,每个输入寄存器都占两个字节,读取的输入寄存器数量由主站读取时指定。 2、发送报文格式 更详细的格式如下: 从站地址+功能码+起始地址高位+起始地址低位+寄存器数量高位+寄存器数量低位+…

备战求战 | 笔试强训6

目录 一、选择题 二、编程题 三、选择题题解 四、编程题题解 一、选择题 1、十进制变量i的值为100&#xff0c;那么八进制的变量i的值为&#xff08;&#xff09; A. 146 B. 148 C. 144 D. 142 2、执行下面语句后的输出为 int I1; if(I<0)printf("****\n") …

全志F1C200S嵌入式驱动开发(串口驱动)

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】 对于uboot、kernel和rootfs来说,他们的串口输出一般都是uart0。一般这么做,是没有问题的。只不过我们自己买的这块f1c200s电路板,设计者把uart转ttl的接口,改接到了uart1上面。…