CF1593D1题解
CF1593D1题解
题意
把题意转换一下就可以得到:给定一个数列 a1,a2,a3,⋯,an,要求一个数列 b(b 中的数为非负整数)和一个正整数 k,使得 a[1]−b[1]×k=a[2]−b[2]×k=⋯=a[n]−b[n]×k。若有无数多个 k,请输出 −1。(有多组数据)
思路
首先直接讲解法:将数组去重并判断是否有无数多个 k 之后再两两作差求最大公因数即可。那么就有以下解释:
- 咋去重?答:建立一个 vis 数组和 a 数组,vis 数组为判断一个数是否已经出现过,a 数组为去重之后的数组,如果一个数没有出现过,就录入到数组 a 中。
- 咋判断有无数多个 k?答:在去重的时候,用一个 len 记录去重之后的数组长度,如果为 1,也就是去重以前所有数都相同,所以 k 为任意数,输出 −1。
- 为啥用两两相减求最大公因数?接下来我就来证明。
证明:
∵ai−bi×k=aj−bj×k
∴ai−aj=k×(bi−bj)
∴ai≡aj(modk)
∴a1≡a2≡a3≡⋯≡an(modk)
∴ 只要两两作差求最大公因数即可。
总结
- 多组数据。
- 换行。
- 两两作差求最大公因数。
- 去重。
- 特判。
代码
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
int T;
int n,a[45],ans,cnt,len;
bool vis[2000005];
//a数组为去重之后的数组
//cnt为临时变量。
//len为去重之后的数组长度。
//vis数组是一个数字是否出现过的统计数组,去重要用。
int gcd(int a, int b){//求最大公因数
if(b==0) return a;
return gcd(b,a%b);
}
int main(){
scanf("%d",&T);
while(T--){
scanf("%d",&n);
memset(vis,0,sizeof(vis));//一定要重置。
len=0;
for(int i=1; i<=n; i++){
scanf("%d",&cnt);
if(vis[cnt+1000001]==0){//以前这个数没出现过(这个数是新的)。
vis[cnt+1000001]=1;//标记为出现过(旧的)。
a[++len]=cnt;//录入a数组
}
}
if(len==1){//去重之后只有1个数,也就是去重以前所有数都相同,所以k为任意数,输出-1。
printf("-1\n");//别忘了换行
continue;
}
ans=abs(a[2]-a[1]);//取绝对值
for(int i=2; i<len; i++)
for(int j=i+1; j<=len; j++)
ans=gcd(ans,abs(a[j]-a[i]));
printf("%d\n",ans);
}
return 0;
}
附(选看)
怎么求最大公因数
方法 1:用唯一分解定理,先分解质因数,然后求最大公因数。
令 a=pa11×pa22×pa33×⋯pamm,b=pb11×pb22×pb33×⋯pbmm。
则 gcd(a,b)=pmin(a1,b1)1×pmin(a2,b2)2×pmin(a2,b2)2×⋯pmin(am,bm)m。
方法 2:九章算术 ∙ 更相减损术。
∀a,b∈N,b≤a,有 gcd(a,b)=gcd(b,a−b)=gcd(a,a−b)。
∀a,b∈N,有 gcd(2a,2b)=2gcd(a,b)。
证明:
对于 a,b 的任意公约数 d,因为 d|a,d|b,所以 d|(a−b)。因此,d 为 b,(a−b) 的公约数。反之亦成立。
方法 3:欧几里得算法。
∀a,b∈N,b≠0,gcd(a,b)=gcd(b,amodb)。
证明:
若 a<b,则 gcd(b,amodb)=gcd(a,b),命题成立。
若 a≥b,设 a=q×b+r,其中 0≤r<b。显然 r=amodb。对于 a,b 的任意公约数 d,因为 d|a,d|q×b,所以 d|(a−qb)。即 d|r,因此,d 为 b,r 的公约数。反之亦成立。所以他们的最大公因数相等。
代码实现:
int gcd(int a, int b){
if(b==0) return a;
return gcd(b,a%b);
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】