51nod 1439:互質對 容斥原理 深搜!!!
有n個數字,a[1],a[2],…,a[n]。有一個集合,剛開始集合為空。然後有一種操作每次向集合中加入一個數字或者刪除一個數字。每次操作給出一個下標x(1 ≤ x ≤ n),如果a[x]已經在集合中,那麼就刪除a[x],否則就加入a[x]。
問每次操作之後集合中互質的數字有多少對。
注意,集合中可以有重複的數字,兩個數字不同當且僅當他們的下標不同。
比如a[1]=a[2]=1。那麼經過兩次操作1,2之後,集合之後存在兩個1,裡面有一對互質。
Input
單組測試資料。 第一行包含兩個整數n 和 q (1 ≤ n, q ≤ 2 × 10^5)。表示數字的種類和查詢數目。 第二行有n個以空格分開的整數a[1],a[2],…,a[n] (1 ≤ a[i] ≤ 5 × 10^5),分別表示n個數字。 接下來q行,每行一個整數x(1 ≤ x ≤ n),表示每次操作的下標。
對於每一個查詢,輸出當前集合中互質的數字有多少對。Input示例
樣例輸入1 5 6 1 2 3 4 6 1 2 3 4 5 1 樣例輸入2 2 3 1 1 1 2 1Output示例
樣例輸出1 0 1 3 5 6 2 樣例輸出2 0 1 0
如果已知當前集合中互質的個數為ans,那麼加入或者刪除某個元素最後的結果也就是ans加上或減去該元素與集合中元素互質的個數。
所以要求的就是一個數與集合中各個數之間互質的個數。
做法是把每一個數拆成各個質數因子的乘積,然後對這些質數進行排列組合,那6來說,先假設將所有元素都是與6互質的,然後這裡面減去因子有2的(與6一定不互質了),再減去因子有3的,但是這裡面減的話,有部分減重複了,就是因子既有2又有3的,所以又要加上因子6的個數,使用容斥原理最終得到結果。
程式碼:
#include <iostream> #include <algorithm> #include <cmath> #include <vector> #include <string> #include <cstring> #pragma warning(disable:4996) using namespace std; #define maxn 500005 vector<int>prime[maxn]; int cnt[maxn], v[maxn], a[maxn], flag[maxn]; int x; int n, q; long long ans; void dfs(int num,int mul,int symbol,int add_minus) { if (num == prime[x].size()) { if (add_minus == -1) cnt[mul]--; ans += symbol*cnt[mul]; if (add_minus == 1) cnt[mul]++; return; } dfs(num + 1, mul, symbol, add_minus); dfs(num + 1, mul*prime[x][num], -symbol, add_minus); } int main() { //freopen("i.txt", "r", stdin); //freopen("o.txt", "w", stdout); int i, j; for (i = 2; i < maxn; i++) { if (v[i])continue; for (j = i; j < maxn; j = j + i) { v[j] = 1; prime[j].push_back(i); } } cin>>n>>q; for (i = 1; i <= n; i++) { cin>>a[i]; } ans = 0; for (i = 1; i <= q; i++) { cin>>x; if (flag[x] == 0) { flag[x] = 1; x = a[x]; dfs(0, 1, 1, 1); } else { flag[x] = 0; x = a[x]; dfs(0, 1, -1, -1); } cout<<ans<<endl; } //system("pause"); return 0; }
相關推薦
51nod 1439:互質對 容斥原理 深搜!!!
收藏 取消關注 有n個數字,a[1],a[2],…,a[n]。有一個集合,剛開始集合為空。然後有一種操作每次向集合中加入一個數字或者刪除一個數字。每次操作給出一個下標x(
hdu 4135 a到b的範圍中多少數與n互質(容斥)
namespace rim 所有 += ont put contain 質因數 tor Co-prime 題目鏈接:http://acm.hdu.edu.cn/showproblem.php?pid=4135 input
[洛谷P5106]dkw的lcm:尤拉函式+容斥原理+擴充套件尤拉定理
分析 考慮使用尤拉函式的計算公式化簡原式,因為有: \[lcm(i_1,i_2,...,i_k)=p_1^{q_{1\ max}} \times p_2^{q_{2\ max}} \times ... \times p_m^{q_{m\ max}}\] 其實就是分解質因數,丟到那個尤拉函式計算式子裡:
互素,容斥原理,HDU4135 POJ2407 HDU1796
(三道題目的完整程式碼在文章最後) 這幾道題都是有關互素和容斥原理的問題, 要求1~n 中與 m互質的自然數的個數的基本思路是:先找到m的所有質因數然後用容斥原理找出在1~n的範圍內與m互質的數的個數。 以HDU4135(Coprime)為例。點選看原題 該題讓我們找出
51nod 1439 互質對
題目連結 題意: 思路: 題目連結 題意: 給 NN 個數,然後 QQ 次詢問,每次詢問一個 idid ,如果這個 idid 沒有出現過,就在集合中新增一個 a[id]a[id] ,如果出現過就把 a[id]a[id] 刪去,換句話
求N(10^14)以內與N互質的數的和(容斥原理,或者尤拉函式)
#include <iostream> #include <cstring> #include <algorithm> #include <cmath>
容斥原理 —— 求1~n有多少個數與k互質(二進位制演算法詳細解釋&模板)
這裡有一道經典的例題,可以看一下:點選開啟連結 這裡的n可能要大於k的,所以不能用尤拉函式去做。 我們首先把k分解質因數,儲存到p陣列中,num表示質因子的數量。 void pr(int k) //求k的質因子 { num = 0; for (int i = 2 ;
【容斥原理-求區間內與n互質的數】HDOJ Co-prime 4135
Given a number N, you are asked to count the number of integers between A and B inclusive which are relatively prime to N. Two integers are said to be co-
求1~n與x互質的數的個數(6個題、容斥原理)
HDU 4135、POJ 2773、HDU 1695、HDU 2841、ZOJ 2836、HDU 1796 HDU 4135 Co-prime 題意: 求[l,r]與x互質的數的
容斥原理求1到n與k互質個數
參考部落格:傳送門 此處的k<=1e9、 #include<cmath> #include<cstring> #include<cstdio> #include<algorithm> #include<vecto
求1~n中與m互質的數的個數(m>n) 附hdu1695題解(尤拉函式+容斥原理)
int calc(int n,int m) { //求1~n 與m互質的數的個數 int num=getFactors(m); //先將m分解質因數 int sum=0; //先求出不互質的個數,最後用n減去該數 for(int state=1;
51nod 1284 2 3 5 7的倍數 | 容斥原理
using targe pre include mage style 部分 pan 相交 用容斥原理求出不滿足條件的個數cnt,然後用n-cnt就得到答案了。 這裏不滿條件的數就是能整除2,3,5,7這些數的集合並集。要計算幾個集合並集的大小,我們要先將所有單
「2017 山東一輪集訓 Day7」逆序對 - 容斥 - 分塊揹包
我不會整數劃分 考慮dp,轉移方程形如 f ( i
5297 十分優(lie)質的容斥
如果做過簡化版,看到這道題第一反應就是二分答案,找最小的N滿足他前面的數(包含他自己)刪去可以開1到r次方的數之後只剩下n個。但是這道題用二分答案會TLE(不知道寫的好會不會,但是我會)。且找N他前面的數(包含他自己)刪去可以開1到r次方的數之後剩下多少個的方法也很重
組合數學:容斥原理及其應用
容斥原理 例題:從1到1000中不能被5,6,8整除的整數個數。 令P1具有被5整除的性質,P2具有被6整除的性質,P3被8整除性質。 S是前1000個正整數的集合希望求出三個性質同時不滿足的個數 |A1| = floor(1000/5) = 200;|A2| =
容斥原理的(二進位制思想和質因子分解+模板)
#include<iostream> #include<string> #include<cstdio> #include<algorithm> #include<cmath> #include<iomanip
51nod 1407 與與與與 dp+容斥原理
題意 有n個整數,問從他們中取出若干個數字相與之後結果是0的有多少組。 答案比較大,輸出對於 1,000,000,007 (1e9+7)取模後的結果。 1<=n<=1,000,000,
區間互素(篩法尤拉函式模板+容斥原理)(1695)
GCD Time Limit: 6000/3000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 8818 Accepted Submission
求a~b內與n互素的數的個數 容斥原理
題意:給定你一個數n,請你統計出在[a,b]這個區間中和n互質的數的個數。兩個數互質當且僅當他們除了1之外沒有其他的公共因子或者他們最大的公共因子是1。1和任何數是互素的。 輸入:第一行輸入一個整
離散數學:容斥原理
這題答案有點問題,並不能滿分通過,想滿分的移步吧,只提供一個思路,思路是沒問題的 提示:求兩個整數a, b的最小公倍數lcm(a,b),可以利用a, b的最大公約數gcd(a,b)來完成,即lcm(a, b) = a*b/gcd(a, b) gcd可以這