同余最短路经典套路
给定 n n n个数,每个数都可以选多次(也可以不选),将所有选中的数相加。问最终能够组成多少种不同的数或者不能组成的最大数或者。。。
形如 a x + b y + c z + . . = k ax+by+cz+..=k ax+by+cz+..=k,其中 a , b , c a,b,c a,b,c表示对应的数的选中次数。
从最简单的 a x + b y = k ax+by=k ax+by=k入手分析:
b y = k − a x by=k-ax by=k−ax b y % x ∈ [ 0 , x − 1 ] by\%x \in{[0,x-1]} by%x∈[0,x−1] i ⇒ ( i + y ) % x , c o s t = y , i ∈ [ 0 , x − 1 ] i\Rightarrow(i+y)\%x,cost=y,i\in{[0,x-1]} i⇒(i+y)%x,cost=y,i∈[0,x−1]
也就是说由 b y by by组成的值对 x x x取余,可以将这些值根据余数分为 x x x组,也就是同余类。并且从余数 i i i到余数 ( i + y ) % x (i+y)\%x (i+y)%x的代价是 y y y。
建图,边的信息为 ( i , ( i + y ) % x , y ) , i ∈ [ 0 , x − 1 ] (i, (i+y)\%x, y), i\in{[0,x-1]} (i,(i+y)%x,y),i∈[0,x−1],表示从点 i i i到点 ( i + y ) % x (i+y)\%x (i+y)%x的代价是 y y y(当然也存在 b y % x ≠ i by\%x\ne i by%x=i这种情况)。
d i s [ i ] dis[i] dis[i]表示满足 b y % x = i by\%x=i by%x=i的最小的 b y by by,也就是最少要选取 b b b次 y y y,才能使 b y % x = i , b ≥ 0 by\%x=i,b≥0 by%x=i,b≥0,也就是每个同余类中的最小值。
求 d i s [ ] dis[] dis[]就相当于在图中求最短路(我习惯用spfa),且 d i s [ 0 ] = 0 dis[0]=0 dis[0]=0(因为 0 ∗ y % x = 0 0*y\%x=0 0∗y%x=0)
求完 d i s [ i ] dis[i] dis[i]之后便得到了每个同余类中的最小值 p i p_i pi,很明显 p i + x p_i+x pi+x和 p i p_i p

最低0.47元/天 解锁文章

被折叠的 条评论
为什么被折叠?



