class="markdown_views prism-atom-one-light">
模意义下最短路
挂题解
http://blog.csdn.net/PoPoQQQ/article/details/46605701
using namespace std;
namespace runzhe2000
{
typedef long long ll;
const ll INF = 1ll<<60;
ll dis[N], Bmin, Bmax; bool inq[N];
int ecnt, n, last[N], a[M];
struct edge{int next, to, val;}e[N*M];
void addedge(int a, int b, int c)
{
e[++ecnt] = (edge){last[a], b, c};
last[a] = ecnt;
}
void SPFA()
{
queue<int> q; q.push(0);
for(int i = 0; i < a[1]; i++) dis[i] = INF;
dis[0] = 0;
for(; !q.empty(); q.pop())
{
int x = q.front(); inq[x] = 0;
for(int i = last[x]; i; i = e[i].next)
{
int y = e[i].to;
if(dis[x] + e[i].val < dis[y])
{
dis[y] = dis[x] + e[i].val;
if(!inq[y])q.push(y), inq[y] = 1;
}
}
}
}
ll calc(ll lim, ll a, int b) // 干,没注意到a也要看long long,调了好一会儿
{
if(lim < a) return 0;
else return (lim - a) / b + 1;
}
void main()
{
scanf("%d%lld%lld",&n,&Bmin,&Bmax);
for(int i = 1; i <= n; i++)
{
scanf("%d",&a[i]);
if(!a[i]){i--; n--; continue;}
}
sort(a+1, a+1+n);
for(int i = 0; i < a[1]; i++)
for(int j = 2; j <= n; j++)
addedge(i, (i+a[j])%a[1], a[j]);
SPFA();
ll ans = 0;
for(int i = 0; i < a[1]; i++)
{
if(dis[i] == INF) continue;
ans += calc(Bmax, dis[i], a[1]);
ans -= calc(Bmin-1, dis[i], a[1]);
}
printf("%lld
",ans);
}
}
int main()
{
runzhe2000::main();
}