zoukankan      html  css  js  c++  java
  • cf round 482D Kuro and GCD and XOR and SUM

    题意:

    开始有个空集合,现在有两种操作:

    $(1,x)$:给集合加一个数$x$,$x leq 10^5$;

    $(2,x,k,s)$:在集合中找一个$a$,满足$a leq s-x$,而且$k|gcd(a,x)$;现在需要找满足条件的$a$,它异或$x$的值最大。$x,k,s leq 10^5$

    操作数$q leq 10^5$

    这道题就是看你想到一个算法有没有去算算实际复杂度

    我们发现,对于所有在$[1,10^5]$的$i$,$10^5$之内的$i$的倍数的个数和,并不是很大,只有$2*10^7$左右

    然后就维护$10^5$个trie就好了……

    //Serene
    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<cstdlib>
    #include<cstdio>
    #include<cmath>
    using namespace std;
    #define ll long long
    #define db double
    #define For(i,a,b) for(int i=(a);i<=(b);++i)
    #define Rep(i,a,b) for(int i=(a);i>=(b);--i)
    const int maxn=2e5+7,maxm=2e7+7,W=1e5,U=16,INF=0x3f3f3f3f;
    int n,root[maxn],tot=W;
    int son[maxm][2],minnum[maxm];
    bool vis[maxn];
    
    char cc; ll ff;
    template<typename T>void read(T& aa) {
    	aa=0;cc=getchar();ff=1;
    	while((cc<'0'||cc>'9')&&cc!='-') cc=getchar();
    	if(cc=='-') ff=-1,cc=getchar();
    	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
    	aa*=ff;
    }
    
    int prime[maxn],totp,num[maxn];
    bool ok[maxn];
    void get_p() {
    	For(i,2,W) {
    		if(!ok[i]) prime[++totp]=i,num[i]=i;
    		For(j,1,totp) {
    			if(prime[j]>W/i) break;
    			ok[i*prime[j]]=1;
    			num[i*prime[j]]=prime[j];
    			if(i%prime[j]==0) break;
    		}
    	}
    }
    
    void add(int pos,int x) {
    	minnum[pos]=min(minnum[pos],x);
    	int r;
    	Rep(i,U,0) {
    		r=(x>>i)&1;
    		if(!son[pos][r]) minnum[son[pos][r]=++tot]=x;
    		pos=son[pos][r]; minnum[pos]=min(minnum[pos],x);
    	}
    } 
    
    int zz[maxn];
    void get_add(int x) {
    	if(vis[x]) return; vis[x]=1;
    	int s=1,t=1,p,now,y,o=x; zz[1]=1;
    	while(x!=1) {
    		p=num[x]; now=0; y=1;
    		while(x%p==0) x/=p,now++;
    		For(i,1,now) {
    			y*=p;
    			For(j,1,s) zz[++t]=zz[j]*y;
    		}
    		s=t;
    	}
    	For(i,1,t) add(zz[i],o);
    }
    
    int get_ans(int x,int pos,int v) {
    	if(x%pos||minnum[pos]>v) return -1;
    	int r;
    	Rep(i,U,0) {
    		r=(x>>i)&1;
    		if(minnum[son[pos][r^1]]<=v) pos=son[pos][r^1];
    		else pos=son[pos][r];
    	}
    	return minnum[pos];
    }
    
    int main() {
    	read(n); int op,k,x,v;
    	get_p();
    	For(i,0,W) minnum[i]=INF;
    	For(i,1,n) {
    		read(op); read(x);
    		if(op==1) get_add(x);
    		else {
    			read(k); read(v);
    			printf("%d
    ",get_ans(x,k,v-x));
    		}
    	}
    	return 0;
    }
    

      

  • 相关阅读:
    java-mybaits-00503-延迟加载
    java-mybaits-00502-案例-映射分析-一对一、一对多、多对多
    java-mybaits-00501-案例-映射分析-订单商品数据模型
    java-mybaits-00402-Mapper-动态sql-if、where、foreach、sql片段
    数据结构与算法实验题7.1 M 商人的求救
    HDOJ 1075
    HDOJ 1856
    HDOJ 3790
    HDOJ 1869
    HDOJ 1870
  • 原文地址:https://www.cnblogs.com/Serene-shixinyi/p/9092812.html
Copyright © 2011-2022 走看看