题意:给你n组,每组两个数字,要你给出一个数,要求这个是每一组其中一个数的因数(非1),给出任意满足的一个数,不存在则输出-1。

思路1:刚开始乱七八糟暴力了一下果断超时,然后想到了把每组两个数相乘,然后求每组的GCD,那么这个GCD就是因数的乘积(如果GCD==1就输出-1)。然后打个2e5的素筛表,然后找到GCD的一个素数因数。做到这里好像没问题了,然而,分分钟会被hack,问题出在哪里了?显然啊,打素数表只用2e5的范围,但是因数还包括自己本身啊!所以一旦GCD大于2e5我们就找不到答案了,那么我用一个set来储存遇到的大于2e5的数,如果素筛没找到,那就去set里遍历就行了。

思路2:还是那个问题,大于2e5的素数怎么解决。大佬告诉我一个方法,把第一组数据质因数分解,如果分解到最后发现第一组数据的质因数出现了大于2e5的素数,那么就把他存起来,在后面判断。

混合场很不友好,然而我并没有报名,帮别人掉分(逃

代码1:

#include<stack>
#include<vector>
#include<queue>
#include<set>
#include<cstring>
#include<string>
#include<sstream>
#include<iostream>
#include<algorithm>
#define ll long long
#define ull unsigned long long
using namespace std;
const int maxn = 2e5+;
const int seed = ;
const int MOD = ;
const int INF = 0x3f3f3f3f;
int pr[maxn],p[maxn],pn;
set<ll> st;
void get(){
pn = ;
memset(pr,,sizeof(pr));
for(int i = ;i < maxn;i++){
if(!pr[i]){
p[pn++] = i;
for(ll j = (ll) i * i;j < maxn;j += i){
pr[j] = ;
}
}
}
}
ull gcd(ull a,ull b){
return b == ? a : gcd(b,a % b);
}
int main(){
int n;
get();
st.clear();
scanf("%d",&n);
ull u,v;
scanf("%lld%lld",&u,&v);
if(u >= maxn) st.insert(u);
if(v >= maxn) st.insert(v);
ull GCD = u*v;
bool flag = true;
for(int i = ;i <= n;i++){
scanf("%lld%lld",&u,&v);
if(u >= maxn) st.insert(u);
if(v >= maxn) st.insert(v);
GCD = gcd(GCD,u * v);
if(GCD == ){
flag = false;
break;
}
}
if(flag){
for(int i = ;i < pn && p[i] * p[i] <= GCD;i++){
if(GCD % p[i] == ){
printf("%d\n",p[i]);
return ;
}
}
for(set<ll>::iterator it = st.begin(); it != st.end();++it){
ll u = *it;
if(GCD % u == ){
printf("%lld\n",*it);
return ;
}
}
printf("%lld\n",GCD);
}
else printf("-1\n");
return ;
}

代码2:

/*
author :竹攸
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std; const int maxn = 2e5+;
typedef long long ll;
ll p[maxn],num[maxn],k,a[maxn],b[maxn]; void prime(){
for(int i = ; i < maxn; i++){
if(!num[i]){
for(ll j = 1LL*i*i; j < maxn; j+=i){
num[j] = ;
}
}
}
k = ;
for(int i = ; i < maxn;i++){
if(!num[i])
p[++k] = i;
}
} ll gcd(ll a,ll b){
return b == ?a:gcd(b, a%b);
} int main(){
int n;
ll x, y, a, b, sa, sb;
prime();
while(scanf("%d",&n)!=EOF){
scanf("%lld%lld",&x,&y);
num[] = x*y;
if(n == ){ //n等于1的时候先输出
printf("%lld\n",x);
continue;
}
for(int i = ; i <= k&& x >= p[i]; i++){ //判断x中是否存在大于2e5的素数
while(x % p[i] == ){
x /= p[i];
}
}
if(x == )
a = 2e9+;
else
a = x;
for(int i = ; i <= k&& y >= p[i]; i++){ //y与x 同理
while(y % p[i] == ){
y /= p[i];
}
}
if(y == )
b = 2e9+;
else
b = y;
sa = sb = ;
for(int i = ; i <= n; i++){
scanf("%lld%lld",&x,&y);
num[i] = x*y;
if(x % a == || y % a == )
sa++;
if(y % b == || x % b == )
sb++;
}
if(sa == n){
printf("%lld\n",a);
continue;
}
else if(sb == n){
printf("%lld\n",b);
continue;
}
ll Gcd = num[];
for(int i = ; i <= n; i++)
Gcd = gcd(num[i],Gcd);
int ans = ;
for(int i = ; i <= k;i++){
if(Gcd % p[i] == ){
ans = p[i];
break;
} }
if(ans == && Gcd != )
printf("%lld\n",Gcd);
else if(ans == && Gcd == )
printf("-1\n");
else
printf("%d\n",ans);
}
return ;
}

最新文章

  1. linux基本知识
  2. Java异常处理机制 try-catch-finally 剖析
  3. WPF下制作的简单瀑布流效果
  4. ASIHTTPRequest 在release(打包)模式下数据获取或post失败问题
  5. IOS播放音频 AVAudioPlayer(实例)
  6. MVC Razor 语法(转)
  7. [转] JavaScript 原型理解与创建对象应用
  8. Android --- 字符串\n的换行问题
  9. 发短信utils
  10. python调试
  11. [Mysql]由Data truncated for column联想到的sql_mode配置
  12. cglib根据数据动态生成对象
  13. CMake根据平台移植检查设置文件编译选项
  14. 使用Pycharm创建一个Django项目
  15. RPA基础
  16. 用 Django 管理现有数据库
  17. [SHOI2006]color 有色图[群论、组合计数]
  18. java 实现websocket
  19. Effective java 系列之避免过度同步和不要使用原生态类型,优先考虑泛型
  20. each的break

热门文章

  1. 简单的网络爬虫程序(Web Crawlers)
  2. 微软雅黑的Unicode码和英文名
  3. TextureMerger1.6.6 三:Bitmap Font的制作和使用
  4. 【BZOJ1901】Zju2112 Dynamic Rankings 主席树+树状数组
  5. 【Android】Android 发送短信和打电话的方法
  6. 豆瓣api开发
  7. 310实验室OTL问题----将写好的C++文件转换成Python文件,并将数据可视化
  8. WebSocket学习记录
  9. SmartSprites 智能批量合并 CSS 雪碧图
  10. cocos2d 特效