• Educational Codeforces Round 89 (Rated for Div. 2) D. Two Divisors (数学)


    • 题意:有\(n\)组数,对于每组数,问是否能找到两个因子\(d_{1},d{2}\),使得\(gcd(d_{1}+d_{2},a_{i}=1)\),如果有,输出它们,否则输出\(-1\).

    • 题解:对于这题,首先我们要推两个gcd的公式:

      ​ 1) $gcd(a,b)=gcd(a+b,b) $.

      ​ 2) 若\(gcd(a,c)=1 \ => gcd(a,bc)=gcd(a,b)\).

      这两个公式应该都很容易证明.

      因此我们推出:若\(gcd(x,y)=1\),则:\(gcd(x+y,xy)=1\).

      所以我们就可以对\(a_{i}\)质因数分解,得到:\(p_{1}^{k1},p_{2}^{k2}.....p_{n}^{kn}\).

      我们令\(d_{1}=p_{1}^{k1}\),\(d_{2}=\frac{a_{i}}{d_{1}}\)即可.

      下面给出公式的证明过程:

    • 代码: (用到了欧拉线性筛)

      #include <iostream>
      #include <cstdio>
      #include <cstring>
      #include <cmath>
      #include <algorithm>
      #include <stack>
      #include <queue>
      #include <vector>
      #include <map>
      #include <set>
      #include <unordered_set>
      #include <unordered_map>
      #define ll long long
      #define fi first
      #define se second
      #define pb push_back
      #define me memset
      const int N = 1e7 + 10;
      const int mod = 1e9 + 7;
      const int INF = 0x3f3f3f3f;
      using namespace std;
      typedef pair<int,int> PII;
      typedef pair<ll,ll> PLL;
      
      int n;
      int prime[N];
      int cnt;
      bool st[N];
      int a[N];
      vector<int> v;
      vector<PII> ans;
      
      void get_prime(){
      	for(int i=2;i<=N;++i){
      		if(!st[i]) prime[++cnt]=i;
      		for(int j=1;j<=cnt && prime[j]<=n/i;++j){
      			st[i*prime[j]]=true;
      			if(i%prime[j]==0) break;
      		}
      	}
      }
      
      void divide(int x){
      	 int tmp=x;
           for(int i=1;i<=cnt;++i){
           	if((ll)prime[i]*(ll)prime[i]>(ll)x) break;
           	if(x%prime[i]==0){
           	  int t=1;
           	  while(x%prime[i]==0){
           		x/=prime[i];
           		t*=prime[i];
           	  }
           	  v.pb(t);
           	}
           }
           if(x>1) v.pb(x);
           if(v.size()<2) ans.pb({-1,-1});
           else ans.pb({v[0],tmp/v[0]});	
           v.clear();
      }
      
      int main() {
          ios::sync_with_stdio(false);cin.tie(0);
      	cin>>n;
      	 for(int i=1;i<=n;++i){
      	 	cin>>a[i];
      	 }
      	 get_prime();
      	 for(int i=1;i<=n;++i){
      	 	divide(a[i]);
      	 }
      	 for(auto w:ans) printf("%d ",w.fi);
      	 printf("\n");
      	 for(auto w:ans) printf("%d ",w.se);
      
      
          return 0;
      }
      
  • 相关阅读:
    【软工4】:软件工程和文档
    ER模型图工具:PowerDesigner
    【软工3】:软件工程视频知识总结
    【软工2】:软件开发阶段
    【软工1】:软件计划及软件需求
    【机房收费系统 5】:验收总结(思想)
    【机房收费系统 4】:VB获取标准北京时间,免除时间误差
    网络经济与企业管理(一)
    【机房收费系统 3】:文本框输入数字、小数点、退格键
    .NET Framework
  • 原文地址:https://www.cnblogs.com/lr599909928/p/13110608.html
Copyright © 2020-2023  润新知