這個遞推實在是讓我感到無奈
實際上就是先計算出在l和r的區間中有多少個數有因數k 然後
f[i] 表示的就是在l和r中選出n個數最大公因數是i*k 的方案數
然後 _ll ll = (n_l - 1) / i + 1;
_ll rr = n_r / i;
_ll len = rr - ll + 1;
這幾句話的意思就是算出在n_l 和 n_r的範圍內有多少個數有因數 i * k 然後
f[i] = pow(len, n) - len;
減去len的原因是因為有len種情況是n個都選擇自己,那麼最大公因數就是自己而不是i * k了
然後剪去所有的非法情況就行了
#include
using
namespace
std;
typedef
long
long _ll;
const _ll mod = 1e9+7;
const _ll maxn = 100000;
_ll pow(_ll n, _ll r)
return ret;
}_ll f[maxn+10];
_ll work(_ll n, _ll k, _ll l, _ll r)}}
if(n_l == 1) f[1] ++;
return f[1] % mod;
}int main()
題解 CQOI2015選數
這題做的時候接連想錯了好多次 但是回到正軌上之後依然是乙個套路題。不過這題好像有比莫比烏斯反演更好的做法,莫比烏斯反演貌似是某種能過的暴力 不過能過也就行了吧哈哈。首先我們把數字的範圍要進行縮小 最大公約數為 k 那自然所有選出來的數都必須是 k 的倍數。所以我們改選數為選擇是 k 的多少倍。然後由...
洛谷 CQOI2015 選數 解題報告
我們知道,從區間 l,h l 和 h 為整數 中選取 n 個整數,總共有 h l 1 n 種方案。小 z 很好奇這樣選出的數的最大公約數的規律,他決定對每種方案選出的 n 個整數都求一次最大公約數,以便進一步研究。然而他很快發現工作量太大了,於是向你尋求幫助。你的任務很簡單,小 z 會告訴你乙個整數...
cqoi2015部分題解
只做了前三題。t1 選數 先把題目轉化為求選n個數最大公約數為1,不用說了。假定f i 為選出n個數最大公約數為i的方案數。由於題目中有條件h l 10 5,所以i 10 5即可。令l l 1 i,r h i f i r l n sigma f a i r l 最後的r l為減去全部選擇乙個數的方案...