1 条题解

  • 0
    @ 2022-2-28 13:31:45

    发现 aia_i 很小,一个常见的思路是将等式左右同时模 a1a_1

    然后判断是否存在一种方案使得 ka1+bka_1+b 有解,可以考虑减一张图,编号表示 bb ,那么直接建边判断联通就好了。

    发现不能减,那么对于一个 bb ,找到最小的一个可以凑出的就好了。

    显然可以最短路,然后就做完了。


    代码
    #include<bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    typedef pair<ll,int> pil;
    priority_queue<pil,vector<pil>,greater<pil> > q;
    const int N=5e5+5;
    int n,a[N],vis[N];
    vector<pair<int,int> > e[N];
    ll l,r,dis[N],ans;
    int main(){
    	scanf("%d%lld%lld",&n,&l,&r);
    	for(int i=1;i<=n;i++)scanf("%d",&a[i]);
    	sort(a+1,a+n+1);
    	for(int i=0;i<a[1];i++)
    		for(int j=1;j<=n;j++)
    			e[i].emplace_back((i+a[j])%a[1],a[j]);
    	memset(dis,63,sizeof(dis));
    	dis[0]=0;
    	q.push(make_pair(0,0));
    	while(!q.empty()){
    		int x=q.top().second;
    		q.pop();
    		if(vis[x])continue;
    		vis[x]=1;
    		for(auto i:e[x]){
    			int y=i.first,z=i.second;
    			if(dis[y]>dis[x]+z){
    				dis[y]=dis[x]+z;
    				q.push(make_pair(dis[y],y));
    			}
    		}
    	}
    	for(int i=0;i<a[1];i++){
    		ll L=max(l,dis[i])-i,R=r-i;
    		if(L>R||R<=0)continue;
    		ans+=R/a[1]-(L-1)/a[1];
    	}
    	printf("%lld",ans);
    }
    
    • 1

    信息

    ID
    79
    时间
    1000ms
    内存
    256MiB
    难度
    10
    标签
    递交数
    1
    已通过
    1
    上传者