日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 >

ACM解题的一些技巧和方法

發布時間:2023/12/15 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 ACM解题的一些技巧和方法 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.


參加acm也一段時間了,決定重新總結下自己學到的一些東西,這樣才會收獲得更多。

比賽考驗的不僅僅是知識面,思維能力,編碼能力,更有團隊合作的意識以及心態。平時接觸的題目會涵蓋各個方面的內容,我們都需要有一些適當的解題技巧,在這里總結談一些比較重要的技巧或者方法的運用:1、預處理 2、算法優化 3、STL的運用。

我只是根據自己的學習到的東西來粗略地總結總結,還遠沒有達到那種真正會的水平,如果有任何錯誤或者說得不好的地方請見諒(路過的大牛、大神請無視我.....)

?

編程的技巧著實很多,小到一些基本的簡單操作比如說位運算的運用大到一些好的思想的應用。任何一個技巧的應用都可能給你的程序帶來不一般的在速度或其他方面的變化,就比如說這個位運算符的應用,充分利用的話時間開銷大大減小。

我也曾在一本叫做算法心得的書上看到了這個技巧,老外寫的,非常經典,書沒有說一些我們現在的算法,而是說怎么利用一些簡單卻非常高效的技巧,只是那本書我實在沒有看完…感覺寫的不錯,但我還沒有用過。

?

下面也有一些小技巧(在此引用,感謝這位博主):

http://blog.sina.com.cn/s/blog_a46ca35201013c4n.html

?

下面進入正題:

1、預處理

所謂預處理,顧名思義,就是事先計算好需要的值或事先處理某些東西,有時候你會發現你做一個題目出現了TLE,原因就是重復的計算會導致效率不高(或者說你的預處理不夠“優雅”)。

一、直接把結果預處理:

舉幾個比較簡單的例子:


1、Xtuoj1052
Description
某一個數字集合定義如下:
1. 0屬于這個集合;
2.如果x屬于這個集合,那么2x+1,3x+1也屬于這個集合;
3.集合只包含按增序排列的前100000個元素。
集合按增序排列,根據輸入的元素序號,輸出對應的元素值。
輸入
每行一個整數n(n<100000),表示元素的序號(從0開始記數),如果是-1,則輸入結束。
輸出
每行輸出對應元素的值。
Sample Input
0
1
2
3
4
5
-1
Sample Output
0
1
3
4
7
9

分析:很明顯,不能也不好直接判斷是否存在于這個集合中,只需要把所有存在于這個集合中標記,并且預處理這些元素的序號,之后輸出就行了,那么一次預處理便可以知道所有序號對應的元素了。

#include <iostream> #define MAX 2000001 using namespace std;int a[100010], b[3*MAX]; int main() {int n, i, j;b[0] = 1;for (i = 0; i < MAX; i++)if (b[i] == 1) b[2*i+1] = b[3*i+1] = 1;for (i = 0, j = 0; i < 100000; j++)if (b[j] == 1) a[i++] = j;while (cin >> n, n != 1) cout << a[n] << endl;return 0; }

2、POJ1426

點擊打開鏈接

題意:有k個壞人k個好人坐成一圈,前k個為好人(編號1~k),后k個為壞人(編號k+1~2k),給定m,從編號為1的人開始報數,報到m的人就要自動死去,之后從下一個人繼續 開始新一輪的報數。問當m為什么值時,k個壞人會在好人死亡之前全部死掉?

分析:遇到存在環的題目的時候,可以直接直線化處理。當然也可以直接利用循環鏈表或者數組進行環的模擬,不過這樣的程序寫起來有點復雜。

這個題目直接暴力模擬求解必定TLE,需要一點數學的知識,這在里就不詳細說了,即使這樣,還是會超時,正確的方法便是預處理出僅有的14個答案,但既然已經知道了所有答案,而且又只有14個,那么直接把答案交上去就行了。

#include <cstdio>int ans[15] = {0, 2, 7, 5, 30, 169, 441, 1872, 7632, 1740, 93313, 459901, 1358657, 2504881, 13482720}; int main() {int n;while (scanf("%d", &n), n) printf("%d\n", ans[n]);return 0; }

3、uva12716

點擊打開鏈接

題意:給定一個整數n,求出有多少對整數a,b滿足1<=b<=a<=n且gcd(a,b)=a XOR b.

分析:最容易想到的方法是枚舉a,b,雙重循環加上求gcd,總復雜度為O(n*n*logn),絕對無法承受。如何減少枚舉呢?注意到亦或運算的性質,如果a^b=c,那么a^c=b,既然c為a,b的最大公約數的話,那么我們可以從枚舉a和c出發,那么就是枚舉所有因子c及其可能的倍數a,和素數篩法一樣,這樣復雜度為O(nlogn*logn),n最大為30000000,復雜度還是有點高,怎么減少復雜度呢?這就要通過一點數學知識或者找規律發現了,通過打印出所有滿足條件的a,b,c可以發現a+b=c,所以可以將復雜度降為O(n*logn),但是題目是多樣例輸入,如果每次都需要O(n*logn)計算答案的話,還是會超時,觀察便可得知其實在計算n以內滿足條件的a,b對數時比n小的數以內的對數都已經計算出來了,也就是說不需要重復計算了,那么我們可以通過一次預處理,在計算的過程中統計每個a組合時的對數,之后循環遍歷一次全部加起來就可以知道每個n以內的答案了。


代碼:

#include <cstdio> #include <algorithm> #include <cstring> #include <cmath> using namespace std;const int N = 30000000; int a[N+5]; void pretreat() {for (int i = 1; i <= 15000000; i++) {for (int j = i<<1; j <= N; j += i) {if ((j ^ (j-i)) == i) a[j]++;}}for (int i = 2; i <= N; i++) a[i] += a[i-1]; }int main() {pretreat();int t, ca = 0;scanf("%d", &t);while (t--) {int n;scanf("%d", &n);printf("Case %d: %d\n", ++ca, a[n]);}return 0; }

二、把需要用的預處理

比較常見的基本就是三個:預處理素數、預處理組合數、預處理前綴和。


首先舉個比較經典的例子:素數打表

判斷是否素數有3種方式:O(sqrt(n)的簡單素性測試、埃氏篩法,以及Miller_Rabin 算法進行素數測試。

如果需要進行大量的用到素數或者判斷素數,則可以埃氏篩法打表出所有的素數。


1、xtuoj1237

Description
題目描述
如果n和n+2都是素數,我們稱其為孿生素數,比如3和5,5和7都是孿生素數。給你一個區間[a,b],請問期間有多少對孿生素數?

輸入
第一行是一個整數K(K≤ 10000),表示樣例的個數。以后每行一個樣例,為兩個整數,a和b,1≤a≤b≤5000000。
輸出
每行輸出一個樣例的結果。
樣例輸入
5
1 3
1 10
1 100
1 1000
1 5000000
樣例輸出
0
2
8
35
32463


分析:計算區間內個數的題目一般滿足區間減法性質,但是不能一概而論,具體題目具體分析,就像這題一對孿生素數是跨越了3個數,要分情況考慮。

首先直接標記出所有的素數,令g[x]為1到x+2這個區間內孿生素數的對數,要統計出數量,遍歷一次即可,只需要一次預處理就可以計算出所有的g[x],之后便可以O(1)計算出所有1到x+2這個區間內孿生素數的對數了。

如果輸入的區間長度小于2,那么必定沒有,如果長度大于2,稍加思考便可以得知答案即為g[b-2]-g[a-1]。

#include <cstdio> #include <cmath>const int N = 5000001; int f[N], g[N]; int main() {int up = sqrt(N);for (int i = 2; i <= up; i++)if(!f[i]) for (int j = i*i; j <= N; j += i) f[j] = 1;for (int i = 3; i < N-1; i += 2)g[i+1] = g[i] = g[i-1] + !(f[i]|| f[i+2]);int t;scanf("%d", &t);while (t--) {int a, b;scanf("%d %d", &a, &b);b-a < 2 ? puts("0") : printf("%d\n", g[b-2] -g[a-1]);}return 0; }

2、CF231CTo Add or Not to Add

點擊打開鏈接

題意:給定一個數組,每次可以給任意元素加1,這樣的操作不能超過k次,求操作不超過k次后數組中一個數能夠出現的最多次數,以及能夠以這個次數出現的最小的數。

分析:這個題目明顯具有單調性,這樣的話就可以進行二分搜索求取最大次數了。怎么判斷假定的解是否可行呢?既然只能是加1,而且又不超過k次,那么首先將數組排序,假設搜索的次數為m,那么i從第m個數循環到最后一個數,只要滿足了次數不小于k就立即退出循環,這樣找到的便一定是出現m次的最小的數,但是這個判斷的過程就是第m個數與其之前的m-1個數的差之和要不大于k,如果每次都直接加上差進行判斷必定超時,因為二分搜索加循環判斷的時間復雜度太高,那么最好的優化就是直接之前預處理,求出第1個數到第m個數區間的和,后面判斷的時候直接就是o(1)計算區間的和了。

?

代碼如下:

#include <cstdio> #include <algorithm> #include <cstring> using namespace std;typedef long long LL; const int INF = 0x3f3f3f3f; const int N = 100010; LL a[N], sum[N];int main() {int n; LL k;while (~scanf("%d %I64d", &n, &k)) {for (int i = 1; i <= n; i++) scanf("%I64d", &a[i]);sort(a + 1, a + 1+n);int r = INF, l = 0;sum[1] = a[1];for (int i = 2; i <= n; i++) sum[i] = a[i] + sum[i-1];LL ans;while (r - l > 1) {int m = (r+l) / 2;if (m > n) { r = m; continue; }int flag = 0;for (int i = m; i <= n; i++) {if ((m-1)*a[i] - sum[i-1] +sum[i-m] <= k){flag = 1; ans = a[i];break;}}flag ? l = m : r = m;}printf("%d %I64d\n", l, ans);}return 0; }


三、關于預處理的總結:

預處理的目的是為了減少重復的計算從而減少時間復雜度,有時一個簡單的預處理能使得算法性能顯著提高。首先我們可以按思路直接寫一個程序,如果復雜度太大,那么算法的優化可以從這個過程出發,思考可以對哪個算法的部分進行改進,而預處理便是一種對應的非常重要的技巧。像預處理區間和便是非常常見的,而且正如上面所示的幾個題一樣,一次預處理出全部的答案也是很常見的,要注意思考每個部分的聯系。


2、算法優化:

其實不知道該怎么給這個技巧取名字,算法優化涵蓋的范圍很廣,優化的地方可以有很多,所以總結也不可能全面,就針對自己遇到的一些題來總結下吧,像上面的預處理技巧其實也算是算法優化的一部分,只不過覺得很重要,所以特別分開了。

分為3個部分:

1、減少冗余計算。2、減少計算量。3、優化計算過程。

(1)、減少冗余計算

1、Codeforces659F-Polycarp and Hay

點擊打開鏈接

題意:給定一個矩陣,每個格子有一個數字,操作是改變格子中的數字,使其變小,操作后的矩陣必須滿足以下要求:所有格子中的數字和為k,非零格子中的數字要相同,至少一個格子要保留為原來的數字不變化,所有格子必須聯通,聯通是指所有非零格子都可以通過非零格子到達。


分析:很容易想到搜索來解決。剛開始的思路是,對于k的某一個約數d,如果格子中存在數字d且大于等于d的數字的個數如果大于等于k/di個的話,那么開始進行搜索并判斷是否滿足條件,滿足條件就把上一次走過的的格子全部變為d,其他全部變為0即可。具體是從正反開始枚舉k的每一個因子然后重復上述過程,但各種優化之后最終還是超時了,跑到了第57個樣例,發現方法選取有問題,首先需要枚舉每一個可行的因子,每次枚舉都需要遍歷所有格子,這樣時間復雜度過高。

其實可以換種方式:直接一次遍歷原圖即可,對于格子中的某一數字d,如果它是k的因子的話,那么直接從此開始搜索,判斷是否滿足條件,這樣優化之后復雜度明顯改善,但最后還是超時了,到了第95test,但是這只是一個最直接的處理,算法的優化是無盡的,很重要的一點就是減少冗余,這樣便除去了大量的重復過程,如果每個處理的過程不是常數時間的話,那么這個優化對于時間復雜度的改善是明顯的!!!回到此題,明顯對于某一個數字d,如果搜索完所有可以到達的格子仍然后不符合條件的話,那么這個過程所有與d相等的格子無需在進行搜索處理,標記即可,因為這些格子也必定不符合條件。

?

#include <cmath> #include <cstring> #include <algorithm> #include <cstdio> using namespace std;typedef long long LL; const int N = 1010; LL k, di, tab[N][N]; int n, m, flag = 1, tot, cnt, sum; int vis[N][N], v[N][N]; int dx[] = {1, -1, 0, 0}, dy[] = {0, 0, 1, -1};void DFS(int x, int y) {if (tab[x][y] == di) v[x][y] = 1;//標記數字相等的格子vis[x][y] = sum;if (++cnt == tot) { flag = 0; return ; }if (flag) {for (int i = 0; i < 4 && flag; i++) {int nx = x + dx[i], ny = y + dy[i];if (nx < 1 || nx > n || ny < 1 || ny > m || vis[nx][ny] == sum) continue;if (tab[nx][ny] >= di) DFS(nx, ny);}} }int main() {scanf("%d %d %I64d", &n, &m, &k);for (int i = 1; i <= n; i++)for (int j = 1; j <= m; j++) scanf("%I64d", &tab[i][j]);LL t = k/n/m;for (int i = 1; i <= n && flag; i++) {for (int j = 1; j <= m && flag; j++) {di = tab[i][j];if (k % di == 0 && di >= t && !v[i][j]) {cnt = 0; sum++;tot = k/tab[i][j];DFS(i, j);}}}if (flag) puts("NO");else {puts("YES");for (int i = 1; i <= n; i++) {for (int j = 1; j <= m; j++) printf("%I64d ", vis[i][j] == sum ? di : 0);puts("");}}return 0; }

2、HDU5510-Bazinga

點擊打開鏈接

題意:給定n個字符串,分別s1、s2…..sn,找出最大的i,使得存在一個j(1<=j<i)使得sj不是si的子串。

分析:題目數據量很大,最多500個字符串,而且長度可以達到2000,然后最后50個樣例,估算下可知就算是使用kmp算法,直接暴力也必定超時,但是這種題沒有什么其他的高效解法,只能暴力,那么我們需要從優化算法的角度入手。其實只要稍加優化就能過了。

如果逆著枚舉所有i的話,那么無法優化,最壞情況下還是會枚舉完所有的i,肯定也會超時,順著枚舉i然后減少重復的判斷就可以了??梢灾?#xff0c;如果一個串i是另一個串j的子串的話,那么在枚舉時對于串i便無需在進行匹配了,只需要與j匹配即可,這題出題人肯定也是考察這一點,想想看,對于串的匹配,通常的算法是o(n^2),對于串i,如果前面的串中很多都是i的子串的如果不用判斷的話會減少大量的時間消耗大的重復判斷過程。

?不過值得一提的是使用strstr,或者search居然會比kmp快了近一倍,雖說一般這兩個函數是平方的,但在實際應用中一般比kmp快,但是這種大量的匹配過程為何還會快且快這么多呢?

#include <cstdio> #include <cstring> #include <algorithm> using namespace std;char s[510][2010]; int main() {int t, k = 0;int vis[510];scanf("%d", &t);while (t--) {int n;scanf("%d", &n);for (int i = 1; i <= n; i++) scanf("%s", s[i]);int ans = -1;memset(vis, 0, sizeof(vis));for (int i = 2; i <= n; i++) {for (int j = 1; j < i; j++) {if (!vis[j]) {int leni = strlen(s[i]);if (search(s[i], s[i]+leni, s[j], s[j]+strlen(s[j])) == s[i]+leni) { ans = i; break; }else vis[j] = 1;}}}printf("Case #%d: %d\n", ++k, ans);}return 0; }

(2)、減少計算量

1、uva10976- Fractions Again?!

點擊打開鏈接

題意:給定正整數k,找到所有的正整數x>=y使得1/k=1/x+1/y,并且輸出所有的式子。

分析:暴力枚舉即可,但是枚舉量多大呢?如果枚舉x,推導可知最優也要從k*(k+1)枚舉到2*k,太大了,明顯不可取,但是如果從枚舉y出發,可以知道y<=2*k,枚舉量大大減小,效率足夠高了。

#include <cstdio> #include <algorithm> #include <cstring> #include <utility> using namespace std;typedef pair<int, int> p; p ans[10000];int main() {int n;while (~scanf("%d", &n)){int k = 0;for (int i = 2*n; i >= n+1; i--){int j = n*i/(i-n);if (j*(i-n) == n*i && j >= 2*n && j <= n*(n+1)) ans[k++] = p(j, i);}printf("%d\n", k);for (int i = k-1; i >= 0; i--) printf("1/%d = 1/%d + 1/%d\n", n, ans[i].first, ans[i].second);}return 0; }

?

2、Hdu5128 - The E-pangPalace

點擊打開鏈接

題意:給定n個點,要求從這n個點當中選擇8個點作為頂點來構成2個不相交(不能有任何一個點公共)的矩形,如果無法選出兩個這樣的矩形的話輸出imp,否則輸出這兩個矩形的最大的面積和。

分析:最容易想到的就是預處理出所有的矩形,假設有n個矩形,之后n*n跑一遍,但這樣可能達到C(30,4)*C(30,4)的復雜度,會超時。其實沒必要,類似于折半枚舉(雙向搜索)的思想,只要枚舉矩形的兩個對角點即兩個點就行了,然后判斷另外兩個點是否存在即可。所以枚舉量最多只有C(30,4)了。而且判斷兩個矩形是否相交的話我們不需要分類出所有的情況,從反面考慮,如果一個矩形在另一個矩形的上方或者左方或者下方或者右方的話就說明不相交了。而且另外一點是,對于一個矩形,我們只需要枚舉一次對角頂點的組合,另外一個組合沒必要枚舉,這樣減少了很多不必要的枚舉。而且對于選出的4個點,按照x從左從左至右排列假設為a,b,c,d四個點的話,只有3種組合方式(a,b)與(c,d),(a,c)與(b,d),(a,d)與(b,c),全部枚舉一下就好了。為方便判斷,可以事先給坐標排序,之后枚舉所有大小為4的子集,并且每次對3種組合方式判斷一下取最大值。

這題的一個坑點:一個矩形可能完全包含在另一個矩形中,這種情況下面積取較大者,否則取和。

暴力枚舉不失為一種好辦法,但是過多的枚舉必然會導致效率低下了。所以下手之前可以分析下,看是否可以減少重復的沒必要的枚舉,而且有時候減少這些枚舉還可以保證正確率,就像這題如果枚舉矩形的兩個對角的組合的話可能會導致判斷不全面導致計算錯誤,之前做的時候就是這樣,發現答案變大了,原因是因為考慮不全面,但是其實是沒必要的。而且折半枚舉也是一種重要的思想,因為很多情況下只需要枚舉一部分量,然后另一部分量直接判斷或者進行查找就好了。?

?

#include <cstdio> #include <algorithm> #include <cstring> #define LL long long #define INF 0x3f3f3f3f using namespace std; struct po{ int x, y; bool operator < (const po& a) const{ return x == a.x ? y < a.y : x < a.x; } }p[50]; int vis[210][210]; int check(int i, int j, int k, int l) { int ix = p[i].x, iy = p[i].y, jx = p[j].x, jy = p[j].y; int kx = p[k].x, ky = p[k].y, lx = p[l].x, ly = p[l].y; if (ix == jx || iy >= jy || kx == lx || ky >= ly) return 0; if (!vis[ix][jy] || !vis[jx][iy] || !vis[kx][ly] || !vis[lx][ky]) return 0; if (jx < kx || ix > lx || jy < ky || iy > ly) return (jx - ix) * (jy - iy) + (lx - kx) * (ly - ky); if (ix < kx && kx < jx && ix < lx && lx < jx && iy < ky && ky < jy && iy < ly && ly < jy) return (jx - ix) * (jy - iy); return 0; } int solve(int i, int j, int k, int l) { return max(check(i, j, k, l), max(check(i, k, j, l), check(i, l, j, k))); } int main() { int n; while (scanf("%d", &n), n){ memset(vis, 0, sizeof(vis)); for (int i = 0; i < n; i++) scanf("%d %d", &p[i].x, &p[i].y), vis[p[i].x][p[i].y] = 1; if (n < 8) { puts("imp"); continue; } sort(p, p + n); int k = (1 << 4) - 1; int ans = 0; while (k < 1 << n){ int t[4]; for (int i = 0, j = 0; i < n; i++) if (k & (1 << i)) t[j++] = i; ans = max(ans, solve(t[0], t[1], t[2], t[3])); int x = k & -k, y = k + x; k = ((k & ~y) / x >> 1) | y; } ans ? printf("%d\n", ans) : puts("imp"); } return 0; }

(3)、優化計算過程

在此舉一個數據結構進行算法的優化的例子:
1、codeforces675E ?Trains and Statistic 點擊打開鏈接

?題意:一個城市有n個車站,編號從1到n,在第i號車站只能買到第i+1號到ai號車站的票(ai>=i+1),令P(i,j)為從第i號車站去第j號車站所需要買的最少的票的數量,給定ai,求所有的P(i,j)之和(1<=i<j<=n).

分析:看起來像圖論題,但是無法存儲,考慮其他方法。無后效性,明顯的動態規劃,令dp[i]為從i號車站去之后i+1到n這些車站的總票數最小數量,可以知道需要逆推,狀態轉移即為dp[i] = dp[pos]+n-i-(a[i]-pos),pos為i+1到a[i]這些車站中a[pos]最大的一個編號,知道了狀態轉移還不行,因為需要有大量計算區間最大值的過程,使用線段樹優化即可。

#include <cstdio> #include <algorithm> #include <cstring> using namespace std;typedef long long LL; const int N = 100010; int id[N<<2], a[N]; LL dp[N], ans;void update(int root) {if (a[id[root<<1]] > a[id[root<<1|1]]) id[root] = id[root<<1];else id[root] = id[root<<1|1]; } void build(int root, int l, int r) {if (l == r) { id[root] = l; return ; }int t = (r-l) / 2;build(root<<1, l, l + t);build(root<<1|1, l + t+1, r);update(root); } int query(int l, int r, int L, int R, int root) {if (l > R || r < L) return -1;if (l <= L && R <= r) return id[root];int idls, idrs, t = (R-L) / 2;idls = query(l, r, L, L + t, root<<1);idrs = query(l, r, L + t+1, R, root<<1|1);if (idls == -1) return idrs;if (idrs == -1) return idls;if (a[idls] > a[idrs]) return idls;return idrs; } int main() {int n;scanf("%d", &n);for (int i = 1; i < n; i++) scanf("%d", a+i);a[n] = n; ans = dp[n-1] = 1;build(1, 1, n);for (int i = n-2; i >= 1; i--) {int pos = query(i+1, a[i], 1, n, 1);dp[i] = dp[pos] + n-i - a[i]-pos;ans += dp[i];}printf("%I64d\n", ans);return 0; }


算法優化的總結:

程序時間復雜度過高,除了換更優的算法之外,優化當前的算法也是很重要的。就像上面說明的那樣:減少當前計算過程中的冗余計算,比如說標記,刪除、從減少計算量出發優化,比如說部分枚舉,折半枚舉、或者優化某個 計算的過程,比如說數據結構優化。算法優化思想或者技巧需要知識的積累和對算法過程進行的仔細分析,難以總結全面。要想熟練運用,還得不斷地鍛煉和總結。

3、 STL的高效運用:

不管你是一個ACM競賽者還是一個開發程序員,STL都會是一個非常好的工具。如果能夠充分地利用STL,可以在代碼空間、執行時間和編碼效率上獲得極大的好處,代碼不僅高效簡潔而且看起來特別舒服。


首先粗略介紹下STL:

STL 大致可以分為三大類:算法(algorithm)、容器(Container)、迭代器(iterator)。

STL 容器是一些模板類,提供了多種組織數據的常用方法,例如vector(向量,類似于數組)、list(列表,類似于鏈表)、deque(雙向隊列)、set(集合)、map(映射)、stack(棧)queue(隊列)、priority_queue(優先隊列)等,

通過模板的參數我們可以指定容器中的元素類型。

STL 算法是一些模板函數,提供了相當多的有用算法和操作,從簡單如for_each(遍歷)到復雜如stable_sort(穩定排序)。STL 迭代器是對C 中的指針的一般化,用來將算法和容器聯系起來。幾乎所有的STL 算法都是通過迭代器來存取元素序列進行工作的,而STL 中的每一個容器也都定義了其本身所專有的迭代器,用以存取容器中的元素。有趣的是,普通的指針也可以像迭代器一樣工作。熟悉了STL 后,你會發現,很多功能只需要用短短的幾行就可以實現了。通過STL,我們可以構造出優雅而且高效的代碼,甚至比你自己手工實現的代碼效果還要好。

STL 的另外一個特點是,它是以源碼方式免費提供的,程序員不僅可以自由地使用這些代碼,也可以學習其源碼,甚至按照自己的需要去修改它。

在這里首先例舉ACM經常需要用到的STL容器或算法:

STl容器或適配器等:pair、list、vector、priority_queue、set、map、stack

常用STL 算法庫:sort快速排序算法、二分查找算法、枚舉排列算法 .


在這里只介紹下應用,如果想知道這個容器的具體操作可以去看書或者找度娘,這里不詳細介紹操作了.

①、容器或適配器部分:

1、? pair

相當于一個Struct,訪問方式舉個例子:pair<int,int> p; 那么第一個成員便是p.first、第二個p.second,pair使用起來很方便,簡單快速高效,可以當做一個二元struct使用,而且它定義了比較的方法,先根據第一個成員比較,在根據第二個,所以如果你的比較運算符是這樣,那么你就不需要定義比較函數了,而struct是不能直接進行比較的,構造pair的方法:make_pair。

下面是一個簡單的例子:

#include <cstdio> #include <algorithm> #include <cstring> #include <utility> #include <functional> using namespace std;const int N = 1010; typedef pair<int, int> p; p a[N];int main() {int k = 0;a[k++] = p(3, 4);a[k++] = p(3, 100);a[k++] = p(1, 2);a[k++] = p(4, 10);//首先按第一個成員從大到小排列,當第一個成員相等時,按第二個成員second從大到小排列sort(a, a+k, greater<p>());for (int i = 0; i < k; i++) printf("%d %d\n", a[i].first, a[i].second);return 0; }

2、List

list是一個循環鏈表,其實我并不經常使用。關鍵在于這個容器的特點:快速插入和刪除。作用和vector差不多,但內部是用鏈表實現。

這個容器不支持隨機訪問,你不能[]或者利用通用算法操作,比如說要排序的話你只能利用成員函數比如list.sort(),而且很重要的一點,list的size()函數是線性的,因為是以遍歷函數distance實現的。


下面的這個題便可以用list的O(1)插入和刪除特性暴力解決,簡直是神技般的存在!

Hdu5127-Dogs' Candies

點擊打開鏈接

題意:一個以兩個數字p,q作為單個元素的序列,支持三種操作:

1、 從序列中去掉包含p,q的這兩個數字的元素。

2、向序列中添加包含p,q的這兩個數字的元素。

3、對于給定的x和y,找到一對p,q,使得px+qy最大,輸出這個最大值。

?

分析:這題雖然數據量比較大,但是卻可以暴力解決,據說現場賽時只有10個隊伍過了此題,正解很麻煩,cdq分治+凸包,然而我全都不會…..首先抓住這題的一個特性,題目可能存在大量的插入和刪除操作,而且對于尋找最大值的操作,只能循環遍歷一次,不存在貪心的選取策略能使得枚舉量減少。如果采取不刪除,而直接進行標記的策略便會超時,因為這樣會使得遍歷的時間增加。

根據以上的分析,抓住題目的特征,選取合適的方法,選用list作為容器來存儲。運行時間不到時限的一半,簡直神奇,如果選取其他的容器也都會超時。也許這就是傳說中的暴力姿勢比較好吧….

#include <cstdio> #include <algorithm> #include <cstring> #include <list> #include <utility> using namespace std;typedef long long LL; typedef pair<LL, LL> p; list<p> l;int main() {int n;while (scanf("%d", &n), n) {l.clear();for (int i = 0; i < n; i++) {LL a, b;int t;scanf("%d %I64d %I64d", &t, &a, &b);if (t == 1) l.push_back(p(a, b));else if (t == -1) l.erase(find(l.begin(), l.end(), p(a, b)));else {list<p>::iterator i = l.begin();LL ans = i->first * a + i->second * b;for (++i; i != l.end(); i++) ans = max(ans, i->first * a + i->second * b);printf("%I64d\n", ans);}}}return 0; }

3、vector

可以說這是一個STL的神器,相當于一個不定長數組,利用這個你可以添加任意多的元素,容器以連續數組的方式存儲元素序列,可以將vector 看作是以順序結構實現的線性表。當我們在程序中需要使用動態數組時,vector將是一個理想的選擇。這個完全相當于把一個數組當成一個元素來進行使用了,可以直接相等,賦值操作等。

在這里介紹幾個比較經典的使用:

1、利用vector防止遞歸爆棧。2、利用vector來實現鄰接表(通常是vector<int>G[N],但這種方式可能會因為存儲量巨大然后vector的容量擴展導致TLE)3、利用vector存儲空間占用比較大的矩陣。

vector高效的原因在于配置了比其所容納的元素更多的內存,但其內存重新配置會花很多時間,(在這里順便說下,像new和malloc等函數要慎用,這屬于用時間開銷代價換取空間的舉措,非常容易TLE),vector確實非常好用,合理使用實則幫助很大。

Vector算是應用得最多的一個stl容器了,例子太多了,在此就不舉了.....

?

4、priority_queue:

這個也可以說是一個神器,優先隊列其實就是堆,在優先隊列中,元素被賦予優先級。當訪問元素時,具有最高優先級的元素最先被刪除。優先隊列具有最高級先出(first in, largest out)的行為特征。在這里說下這個怎么進行重載的問題。

兩種方式:

一、直接在struct或者class內部定義,那么你定義時直接指明元素類型就好了,因為你是定義了比較函數的。二、定義比較結構。

//內部定義: struct node{int x, y;node(int x = 0, int y = 0) : x(x), y(y) {}bool operator < (const node &a) const { return x > a.x; } }; priority_queue<node> q; //定義比較結構 struct node{int x, y;node(int x = 0, int y = 0) : x(x), y(y) {} }; struct cmp {bool operator () (const node &a, const node &b) { return a.x< b.x; } }; priority_queue<node, vector<node>,cmp> q;

具體點就是可以用來貪心或者加速搜索,下面是對應的兩個題:

(1)、貪心


優先隊列最常用的就是貪心,舉個例子。

poj2010-Moo University - Financial Aid ? ??

?點擊打開鏈接

題意:有c只奶牛,現在要招募n只進動物學校,第i只奶牛的分數為si,需要的資金幫助為ai,現在有總共為f的資金,問招募到的n只奶牛中中位數最大是多少?

分析:采取貪心策略,盡量選擇大的,首先按分數從小到大排個序,之后從大到小枚舉中位數,所以我們要知道當前分數作為中位數下,需要的資金總和最小是多少。令l[i]表示選取第i+1號奶牛作為中位數時分數比它小的n/2頭奶牛需要的資金幫助的最小值,令r[i]表示選取第i-1號奶牛作為中位數時分數比它大的n/2頭奶牛需要的資金幫助的最小值。遍歷時用優先隊列存儲當前的分數,貪心地換掉需要的資金多的奶牛,一次預處理r[i]和l[i]即可,總的時間復雜度為O(nlogn)

#include <cstdio> #include <algorithm> #include <cstring> #include <queue> using namespace std;const int N = 100010; int l[N], r[N]; struct calf {int s, a; }ca[N]; bool cmp(calf x, calf y) { return x.s < y.s; }int main() {int n, c, f;scanf("%d %d %d", &n, &c, &f);for (int i = 1; i <= c; i++) scanf("%d %d", &ca[i].s, &ca[i].a);sort(ca+1, ca+1+c, cmp);n >>= 1;priority_queue <int> q;int sum = 0;for (int i = 1; i <= n; i++) q.push(ca[i].a), sum += ca[i].a;l[n] = sum;for (int i = n+1; i <= c-n-1; i++) {if (ca[i].a >= q.top()) l[i] = sum;else {sum -= q.top() - ca[i].a;q.pop(); q.push(ca[i].a);l[i] = sum;}}sum = 0;while (!q.empty()) q.pop();for (int i = c; i >= c-n+1; i--) q.push(ca[i].a), sum += ca[i].a;r[c-n+1] = sum;for (int i = c-n; i >= n+2; i--) {if (ca[i].a >= q.top()) r[i] = sum;else {sum -= q.top() - ca[i].a;q.pop(); q.push(ca[i].a);r[i] = sum;}}int ans = -1;for (int i = c-n; i >= n+1; i--) {if (r[i+1] + l[i-1] + ca[i].a <= f) {ans = ca[i].s;break;}}printf("%d\n", ans);return 0; }

(2)、加速搜索

csu1780 -?簡單的圖論問題

點擊打開鏈接

這題很明顯屬于搜索題,bfs廣搜即可,但是需要找到權值最小的路徑的話,那么我們需要使用優先隊列來加速搜索和求解答案。每一步優先選擇權值小的結點來拓展狀態,且結點中記錄上一次擴展狀態時的方向,而且給一個點標記去重的需要考慮四個方向的狀態。

#include <cstdio> #include <cstring> #include <algorithm> #include <vector> #include <utility> #include <queue> #define INF 0x3f3f3f3f #define LL long long using namespace std; struct po{ int x, y, w, di; bool operator > (const po &a)const {return w > a.w;} }; int n, m, vis[505][505], v[505][505][4]; int maze[510][510], r1, c1, r2, c2, t; char st[5]; int dx[] = {1, -1, 0, 0}, dy[] = {0, 0, 1, -1}; int bfs() { priority_queue <po, vector<po>, greater<po> > q; q.push((po){r1, c1, maze[r1][c1], 0}); memset(vis, 0, sizeof(vis)); vis[r1][c1] = 1; while (!q.empty()){ po t = q.top(); q.pop(); if (t.x==r2 && t.y==c2) return t.w; for (int i = 0; i < 4; i++){ int nx = t.x+dx[i], ny = t.y+dy[i]; if (nx<1 || nx>n || ny<1 || ny>m || vis[nx][ny] || maze[nx][ny]==-1) continue; q.push((po){nx, ny, t.w+maze[nx][ny], 0}); vis[nx][ny] = 1; } } return -1; } int bfs1() { memset(v, 0, sizeof(v)); priority_queue <po, vector<po>, greater<po> > q; q.push((po){r1, c1, maze[r1][c1], -1}); v[r1][c1][0] = v[r1][c1][1] = v[r1][c1][2] = v[r1][c1][3] = 1; while(!q.empty()){ po t = q.top(); q.pop(); if (t.x==r2 && t.y==c2) return t.w; for(int i = 0;i < 4;i ++){ if(i == t.di) continue; int nx = t.x+dx[i], ny = t.y+dy[i]; if(nx<1 || nx>n || ny<1 || ny>m || v[nx][ny][i] || maze[nx][ny]==-1) continue; q.push((po){nx, ny, t.w+maze[nx][ny], i}); v[nx][ny][i] = 1; } } return -1; } int main() { while (~scanf("%d %d %d %d %d %d", &n, &m, &r1, &c1, &r2, &c2)){ memset(maze, -1, sizeof(maze)); for (int i = 1; i <= n; ++i) for (int j = 1; j <= m; ++j){ scanf("%s", st); if (st[0] != '*') sscanf(st, "%d", &maze[i][j]); } printf("Case %d: %d %d\n", ++t, bfs(), bfs1()); } return 0; }

5、set:

set,顧名思義,集合,無重復元素,插入的元素自動按增序排列。
內部實現: 紅黑樹,一種平衡的二叉排序樹,其Compare 函數,類似于qsort 函數里的那個Compare 函數,作為紅黑樹在內部實現的比較方式。
在這里說下一些成員函數的時間復雜度:
insert() O(logn)、erase()O(logn)、find()O(logn)
lower_bound()O(logn) 查找第一個不小于k 的元素
upper_bound()O(logn) 查找第一個大于k 的元素
equal_range()O(logn) 以pair形式返回lower_bound和upper_bound,在需要確定一個增序序列中某一段都是某一值的情況下是非常有效的,這比通用算法更有效。
容器最主要的功能就是判重,也可以進行二分查找。
要允許重復元素,選用multiset即可。
容器性能:set與map的查找、刪除、插入性能都是對數復雜度。

沒有定義比較方式的元素需要進行重載,重載方式和優先隊列一樣。


判重是set的一個最常見的使用。

Uva11572- Unique Snowflakes

點擊打開鏈接

題意:給定一個長度為n序列A,找到一個最長的連續子序列,使得這個序列中沒有相同的元素。

分析:經典的O(n)尺取法,實現過程中需要判斷當前的右端點元素是否存在,利用set判斷即可。s.find(x) != s.end()和s.count(x)都可以。

#include <cstdio> #include <algorithm> #include <cstring> #include <set>using namespace std; int a[1000001]; set<int> s;int main() {int t, n;scanf("%d", &t);while (t--) {scanf("%d", &n);for (int i = 0; i < n; i++) scanf("%d", a+i);s.clear();int st = 0, en = 0, ma = 0;while (en < n) {while (en < n && !s.count(a[en])) s.insert(a[en++]);ma = max(ma, en-st);s.erase(a[st++]);}printf("%d\n", ma);}return 0; }

6、map

這個容器也非常好,和set差不多,pair 組成的紅黑樹(所以比較方式和pair一樣),成員函數復雜度和前者一樣,在這里就不贅述了,容器適用于那些需要進行映射(可以根據Key找到對應的Value,作為hash還是不錯的),因此map是關聯數組。

要允許重復元素,使用multimap。

在這里指出:在C++11里,有unoder和hash的map和set,里面的元素沒有順序.速度比普通的set和map快了很多,但是需要自己重載hash

map最常見的應用就是進行映射。

hdu4460 -?Friend Chains

點擊打開鏈接

題意:給定n個人的名字和這n個人之間的朋友關系,間接相連也算是朋友,如果兩個人之間通過n個人相連,那么這條朋友鏈的長度即為n-1.求一個最小的k,使得對任意兩個人,他們之間的朋友鏈的長度不會超過k。

分析:明顯是求任意兩點之間的最短路,把那個最大的距離找到即可,但是給定的是名字,需要進行映射,用map映射為標號即可。而且這題的邊的權值為1,不需要用優先隊列,用普通隊列即可。值得注意的是,不需要進行n次bfs求取最短路,只需要進行兩次。首先選取一個點x進行最短路的求解,之后找到離x距離最大的那個點y在進行一次最短路的求解即可。因為第一次最短路肯定會求得整個圖中離圖的重心點最遠的那個點,也就是說處于整個圖的最端點。那么之后從這個點出發求得的最短路距離必定是整個圖中任意兩點之間距離的最大值。

#include <cstdio> #include <cstring> #include <string> #include <vector> #include <algorithm> #include <map> #include <queue> using namespace std;const int N = 1010; int vis[N], d[N]; map <string, int> mp; vector<int> G[N];int solve(int x, int n) {int ma = 0, res, cnt = 1;queue<int> q; q.push(x);memset(vis+1, 0, sizeof(int) * (n+1));memset(d+1, 0, sizeof(int) * (n+1));vis[x] = 1;while (!q.empty()) {int t = q.front(); q.pop();for (int i = 0; i < G[t].size(); i++) {int y = G[t][i];if (vis[y]) continue;vis[y] = 1;d[y] = d[t] + 1;if (ma < d[y]) res = y, ma = d[y];q.push(y); cnt++;}}return cnt != n ? -1 : x == 1 ? res: ma; }int main() {int n;while (scanf("%d", &n), n) {mp.clear();for (int i = 1; i <= n; i++) G[i].clear();char s[15], str[15];for (int i = 1; i <= n; i++) scanf("%s", s), mp[s] = i;int m;scanf("%d", &m);for (int i = 1; i <= m; i++) {scanf("%s %s", s, str);G[mp[s]].push_back(mp[str]);G[mp[str]].push_back(mp[s]);}int ans = solve(1, n);ans == -1 ? puts("-1") : printf("%d\n", solve(ans, n));}return 0; }

7、stack:

stack,棧在STL里面它屬于容器適配器,對容器的重新包裝,后進先出結構。

經典使用:單調棧的實現。

poj2559 -?Largest Rectangle in a Histogram

點擊打開鏈接

題意:給定一個柱狀圖,由n個寬為1,長為hi的矩形從左至右依次排列組成,求里面包含的長方形的最大面積是多少?

分析:如果預處理一次區間最小值,暴力也要O(n^2),無法承受,換一種方式,我們可以枚舉每個h[i],求以當前高度作為長度的矩形的最大面積,所以需要做的就是對于固定的h[i],求出左端點L和右端點R,必定有h[L-1]<h[i]和h[R]<h[i],否則總可以更新左右端點,令l[i]為(j<=i且h[j-1]<h[i]的最大的j),r[i]為(j>i且h[j]<h[i]的最小的j). 怎么計算l[i]和r[i]. 思考下就可以知道可以利用棧解決。

考慮計算l[i]的情況,棧中維護的是高度依次減小的標號,也就是如果棧中從上到下的值依次為i,那么i>i+1且h[i]>h[i+1]。對于當前的高度h[i],如果有棧頂的元素h[k]>=h[i],證明左端點可以一直往左移動,不斷地取出棧頂元素,如果棧為空了證明可以移動到最左邊,也就是l[i]=0,否則h[i]=j+1。之所以利用棧求解,是因為每次都要取得左邊第一個高度小的端點和右邊第一個高度小的端點。這樣符合后進先出的性質,模擬下棧的工作情況便可以明白了。正反兩次預處理就可以計算出l和r了,之后遍歷一次高度求取最大值。

這樣的棧稱為單調棧,和單調隊列是類似的。

#include <cstdio> #include <algorithm> #include <cstring> #include <stack> #include <cctype> using namespace std;typedef long long LL; const int N = 100010; stack<int> s; template <class T> inline void read(T &res) {char c; res = 0;while (!isdigit(c = getchar()));while (isdigit(c)) res = res * 10 + c - '0', c = getchar(); } int l[N], r[N]; LL h[N];int main() {int n;while (read(n), n) {for (int i = 0; i < n; i++) read(h[i]);while (!s.empty()) s.pop();for (int i = 0; i < n; i++) {while (!s.empty() && h[s.top()] >= h[i]) s.pop();l[i] = s.empty() ? 0 : s.top()+1;s.push(i);}while (!s.empty()) s.pop();for (int i = n-1; i >= 0; i--) {while (!s.empty() && h[s.top()] >= h[i]) s.pop();r[i] = s.empty() ? n : s.top();s.push(i);}LL ans = 0;for (int i = 0; i < n; i++) ans = max(ans, (LL)h[i] * (r[i] - l[i]));printf("%I64d\n", ans);}return 0; }

②? 、算法庫

主要的頭文件就是#include <algorithm>

1、 sort排序系列:

sort:對給定區間所有元素進行排序(全排)
stable_sort :對給定區間所有元素進行穩定排序,就是相等的元素位置不變,原來在前面的還在前面。
partial_sort :對給定區間所有元素部分排序,就是找出你指定的數目最小或最大的值放在最前面或最后面,比如說我只要找到1000000個數中最大的五個數,那你用這個函數是最好的,排序后最大的五個數就在最前面的五個位置,其他的元素位置分布不確定。
partial_sort_copy:對給定區間復制并排序,和上面的一樣,只是這是指定區間進行復制然后排序的。
nth_element :找出給定區間的某個位置對應的元素,根據比較函數找到第n個最大(小)元素,適用于尋找“第n個元素”。
is_sorted :判斷一個區間是否已經排好序(返回bool值判斷是否已排序)
partition :使得符合某個條件的元素放在前面,劃分區間函數,將 [first, last)中所有滿足的元素置于不滿足的元素前面,這個函數會返回迭代器,設返回的迭代器為 i,則對 [first, i)中的任意迭代器 j,*j滿足給定的判斷,對 [i, last) 中的任意迭代器 k,*k不滿足。
stable_partition :相對穩定的使得符合某個條件的元素放在前面(和上面的一樣,只是位置不變)
這個函數真是絕對的神助,相比qsort沒這么麻煩了。使用時根據需要選擇合理的排序函數即可,所有的排序函數默認從小到大排序,可以定義自己的比較方式。


sort排序十分常見,在此舉個其他排序的例子:

xtu1050-第K個數

Description
給你一個整數序列和若干個問題,問題是這個序列的第i個元素到第j個元素的片斷中的第k大數是什么?比如說給你的序列為(1, 5, 2, 6, 3, 7, 4),問題是(2,5,3),則從第2個元素到第5個元素為(5,2,6,3),排序以后是(2,3,5,6),則第三個數是5。

輸入:
第一行為兩個整數n,m(1 <= n <= 100 000, 1 <= m <= 5 000),表示序列的元素個數和問題的個數,第二行為n個正整數的序列,每個整數為一個32位整數,兩個數之間有一個空格隔開。以后m行為問題,每個問題由三個整數表示i,j,k,第i個元素到第j個元素的片斷中的第k大數是什么?(元素序號從1開始計數,i<=j,1<=k<=j-i+1)

輸出:
每行輸出對應問題的結果。

Sample Input
7 3
1 5 2 6 3 7 4
2 5 3
4 4 1
1 7 3

Sample Output
5
6
3

分析:只需要選擇第k個數,直接nth_element,線性復雜度暴力水過………而且這題解法很多,比如用線段樹等數據結構進行求解會是更優的。

#include <cstdio> #include <algorithm>using namespace std; int a[100010]; int b[100010];int main() {int n, t, i, j, k;scanf("%d %d", &n, &t);for (i = 1; i <= n; i++) scanf("%d", &a[i]);while (t--){copy(a+1, a+n+1, b+1);scanf("%d %d %d", &i, &j, &k);nth_element(b+i, b+i+k-1, b+j+1);printf("%d\n", b[i+k-1]);}return 0; }

2、 二分系列:

二分檢索,復雜度O(log(last-first))
itr =upper_bound(first, last, value, cmp);
//itr 指向大于value 的第一個值(或容器末尾)
itr = lower_bound(first, last, value, cmp);
//itr 指向不小于valude 的第一個值(或容器末尾)
pairequal_range(first, last, value, cmp);
//找出等于value 的值的范圍O(2*log(last– first))
Binary_search(first,last, value)返回bool值,找到則true,否則false。


二分經常會與其他算法結合,二分的應用是也是十分常見的,在這舉個例子說明下找一個數或等于一個數的一個范圍的二分應用:

hdu1496-Equations

點擊打開鏈接

題意:給定a,b,c,d四個數,求有多少對x1,x2,x3,x4滿a*x1^2+b*x2^2+c*x3^2+d*x4^2=0

分析:暴力會超時,把ax1*x1+bx2*x2打表,利用二分查找,排序之后equal_range尋找等于這個值的范圍就行了。

#include <iostream> #include <algorithm> #include <cstring>using namespace std; int val[40010];int main() {pair <int*, int*> p;int a, b, c, d;while (cin >> a >> b >> c >> d) {if( (a > 0 && b > 0 && c > 0 && d > 0) || (a < 0 && b < 0 && c < 0 && d < 0)){cout << 0 << endl;continue;}memset(val, 0, sizeof(val));int k = 0;for (int i = -100; i <= 100; i++){if (i == 0) continue;for (int j = -100; j <= 100; j++) {if (j == 0) continue;val[k++] = a*i*i + b*j*j;}}sort(val, val+k);int cnt = 0;for (int j = -100; j <= 100; j++) {if (j == 0) continue;for (int i = -100; i <= 100; i++) {if (i == 0) continue;int sum = c*j*j + d*i*i;p = equal_range(val, val+k, -sum);cnt += p.second - p.first;}}cout << cnt << endl;}return 0; }

利用二分查找時間復雜度降到了o(n*nlog(n))。當然這個題目可以hash,這是最好的辦法,O(1)查找,復雜度更小了。


3、 排列系列:

這兩個函數都可以用來枚舉字典序排列,那種水題直接用這個就解決了。

在這里貼個網址,看了下,說的挺好的;????????

http://blog.sina.com.cn/s/blog_9f7ea4390101101u.html

?

4、 常用函數:

最后補充下常用函數,//其實是我常用的函數...

copy函數,直接拷貝,比for循環高效,最壞為線性復雜度,而且這個可以說是一個copy族函數,還有類似的滿足一定條件的copy函數如copy_if等。

find、find_i:查找第一個匹配的值或第一個滿足函數使其為true的值位置,沒有返回指定區間的末尾,線性復雜度,還有一些不怎么常用的find族函數就不多介紹了。

count、count_if: 返回匹配或使函數為true的值的個數,線性復雜度。

search,這是尋找序列是否存在于另一個序列中的函數,挺好用的,某些簡單的尋找公共子串的題就可以這樣寫,時間復雜度二次。

reverse,翻轉一個區間的值,我經常遇到需要這種題,直接reverse了,不需要for循環了,主要是方便。

for_each:直接對一個區間內的每個元素執行后面的函數操作,寫起來簡單。

max、min、max_element、min_element:尋找兩個數或者一個區間的最大最小值,都可以添加比較函數參數。

集合操作函數:includes、set_union、set_difference、set_intersection、set_symmetric_difference、前面這些函數的最差復雜度為線性,另外附加一個序列的操作函數merge,相當于歸并排序中的合并函數,時間復雜度為線性,注意這些函數的操作對象都必須是升序的。

這里舉個例子:

#include<cstdio> #include<algorithm> using namespace std; void out(int a) { if (a != -1) printf("%d ",a); } int main() { int a[5] = {1, 8, 10, 52, 100}; int b[5] = {6, 8, 9, 10, 1000}; int c[20]; printf("a集合為:"); for_each(a, a+5, out); puts(""); printf("b集合為:"); for_each(b, b+5, out); puts(""); //判斷b是否是a的子集。 if(includes(a, a+5, b, b+5)) printf("bis a sub set of a\n"); //合并兩個有序序列,必須為合并后的序列分配空間,否則程序會崩潰。 printf("兩個集合的合并序列為:"); merge(a, a+5, b, b+5, c); for_each(c, c+10, out); puts(""); //求兩個集合的并集。 fill(c, c+20, -1); set_union(a, a+5, b, b+5, c); printf("兩個集合的并集為:"); for_each(c, c+10, out); puts(""); //求兩個集合的交集。 fill(c, c+20, -1); set_intersection(a, a+5, b, b+5, c); printf("兩個集合的交集為:"); for_each(c, c+10, out); puts(""); //求兩個集合的差集,這里為a-b。 fill(c, c+20, -1); set_difference(a, a+5, b, b+5, c); printf("a-b的差集為:"); for_each(c, c+10, out); puts(""); //求兩個集合的差集,這里為b-a。 fill(c, c+20, -1); set_difference(b, b+5, a, a+5, c); printf("b-a的差集為:"); for_each(c, c+10, out); puts(""); //求兩個集合的對稱差 set_symmetric_difference(a, a+5, b, b+5,c); printf("兩個集合的對稱差為:"); for_each(c, c+10, out); puts(""); return 0; }

下面的這個題便說明了STL的方便與實用:

codeforces730A - Toda2

點擊打開鏈接

題意:有n個人,每個人有一個rating,目的是使得每個人的rating相同而且盡可能的大,每次可以選取2到5個人,使得每個人的rating減1,如果rating已經為0了,那么不減少,輸出你的操作過程的每一步,每一步為一個01序列,如果選擇了第i個人,那么序列中第i位為1。

分析:模擬題,不過比較麻煩,為方便起見,利用STL實現,思路是每次選取兩到三個人進行rating的減小,然后每次選取rating較大的幾個人減少就行了,如果r全部相等就可以了。

#include <cstdio> #include <algorithm> #include <cstring> #include <set> #include <vector> #include <string> #include <iostream> using namespace std;struct p{int r, id;p(int r = 0, int id = 0) : r(r), id(id) {}bool operator <(const p &x)const { return r > x.r; } }; vector<string> ans; multiset<p> s;int main() {ios::sync_with_stdio(0);int n;cin >> n;for (int i = 0; i < n; i++) {int r;cin >> r;s.insert(p(r, i));}while (s.begin()->r != s.rbegin()->r){string t(n, '0');int num = 2;if(s.count(*s.begin()) == 3) num++;vector<p> tmp;for (int i = 1; i <= num; i++) {p a = *s.begin();s.erase(s.begin());t[a.id] = '1';if (a.r) a.r--;tmp.push_back(a);}s.insert(tmp.begin(), tmp.end());ans.push_back(t);}cout << s.begin()->r << "\n" << ans.size() << "\n";for (int i = 0; i < ans.size(); i++) cout << ans[i] << "\n";return 0; }

③? 、STL使用的總結:

STl不失為一種絕佳工具,合理的使用是一種很好的技巧,但是需要指出不要過分依賴于STL,STL里面函數確實多的你幾乎每個操作都有函數代替,寫起來又簡單。但凡是都有利弊,STl不好的一個地方就是如果碰到某些卡時間、卡空間、各種卡的題目,那些函數的效率問題就大打折扣了,一般手寫的效率會高。
1、STL的容器如queue還有很多函數都比較慢,在碰到那些數據量大的題目時效率確實不高,很容易超時,poj1426 BFS水題吧,用STl容器queue各種超時,一直想不明白,后面自己寫個queue,直接就32ms AC了,通過這個也更加體會到這一點(最致命的一點)
2、STL封裝了大量的數據結構和算法,使用起來一定需要注意,STl容器的操作都是建立在迭代器之上的,迭代器的使用也需要注意,不然各種問題,程序崩潰…
3、STL算法極其多,大致分為搜索、修改、排序、集合與工具等,每一種類中的算法都比較多,有助于我們快速地完成程序設計。
4、使用STL容器時注意使用自帶的成員函數要比通用算法高效很多。
5、STL的算法思想是非常值得借鑒的,你可以去查看以學習。
6、STL也是存在缺點的,沒有提供任何泛型的圖或樹結構,只能自己實現。


終于總結完了~

最后給自己一句話吧:Godhelp those who help themselves.

總結

以上是生活随笔為你收集整理的ACM解题的一些技巧和方法的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

米奇四色影视 | 超碰在线公开 | 黄色在线视频网址 | 日韩午夜三级 | 中文在线a√在线 | 在线观看久久 | 国产精品久久久久久一二三四五 | 国产在线精品区 | 久久久久国产成人精品亚洲午夜 | 国产精品视频你懂的 | 亚洲精品播放 | 人人澡人人草 | 国产精品v a免费视频 | 欧美精品第一 | 免费特级黄毛片 | 高清中文字幕 | 超碰资源在线 | 99视频在线精品免费观看2 | 中文字幕在线观 | 97超碰人人模人人人爽人人爱 | 天堂网中文在线 | 精品在线视频一区二区三区 | 精品久久网站 | 久久综合欧美精品亚洲一区 | 婷婷色综合网 | 久久久国产精品一区二区中文 | 亚洲电影自拍 | 伊人狠狠 | 青青草国产成人99久久 | 日韩在线观看中文字幕 | 日韩av看片 | 久久久国产精品人人片99精片欧美一 | 久久久久久久99精品免费观看 | 久久er99热精品一区二区 | 91亚洲欧美激情 | 99精品视频在线看 | 91精品视频在线看 | 久久国产乱 | 欧美日韩在线播放一区 | 国产在线 一区二区三区 | 欧美在线一二区 | 99久久精品免费一区 | 日韩毛片精品 | 免费视频久久久久久久 | 久久午夜羞羞影院 | 精品视频国产 | 国产专区精品 | 久久黄色小说视频 | 欧美久久影院 | 黄色一级大片免费看 | 日韩在线免费视频观看 | 81精品国产乱码久久久久久 | 亚州性色 | 久久精品99国产精品酒店日本 | av久久久| 亚洲天堂网视频 | 91精品视频播放 | 99精品在线直播 | 天躁狠狠躁 | 亚洲视频1区2区 | 在线不卡a | 久久久麻豆精品一区二区 | 国产又粗又猛又黄又爽的视频 | 久久久久国产精品免费网站 | 大荫蒂欧美视频另类xxxx | 91中文在线视频 | 一区二区三区在线视频观看58 | 欧美精品一区二区三区一线天视频 | 久久一线 | 国产又粗又猛又色又黄视频 | 天天射天天操天天干 | 在线亚洲成人 | 在线观看视频h | 国产精品不卡 | 96久久欧美麻豆网站 | 亚洲精品在线免费 | 91在线免费视频 | 国产在线美女 | 国产精品尤物视频 | 亚洲在线精品视频 | 国产精品日韩久久久久 | 一区二区三区电影大全 | av三级av | 亚洲二级片| 韩国三级一区 | 亚洲精品tv久久久久久久久久 | 亚洲视频久久 | 九9热这里真品2 | 欧美在线视频免费 | 黄色成人免费电影 | 亚洲免费婷婷 | 午夜在线资源 | 亚洲jizzjizz日本少妇 | 一本一本久久a久久精品综合小说 | 国产精品婷婷午夜在线观看 | 美女国产网站 | 99久久日韩精品免费热麻豆美女 | 成人午夜免费福利 | 人人爽人人爽人人爽人人爽 | 久久综合色一综合色88 | 久久国产精品免费一区二区三区 | 免费h漫在线观看 | 国产美女主播精品一区二区三区 | 成人a级黄色片 | 婷婷久久五月天 | 国产伦精品一区二区三区无广告 | 久久精品一区二区三区视频 | 黄色特级片 | 久久经典国产视频 | 99精品免费久久久久久久久日本 | 久久色中文字幕 | 日韩av中文在线 | 成人av网站在线观看 | 91亚·色| 狠狠干天天操 | 亚洲国产精品久久久久 | 91桃色在线播放 | 粉嫩av一区二区三区四区 | 在线看片中文字幕 | 日韩免费一级a毛片在线播放一级 | 亚洲少妇自拍 | 激情六月婷婷久久 | 欧美一区二区三区特黄 | 九色琪琪久久综合网天天 | 国产一级二级视频 | 最近中文字幕免费视频 | 国产一区在线观看免费 | 二区三区精品 | 在线观看国产一区二区 | 色九九视频 | 9热精品 | 中文字幕网站 | 色小说av | 99麻豆视频 | 久久免费在线视频 | 在线亚洲欧美日韩 | 天天爱天天舔 | 亚洲国产视频在线 | 久久久精品福利视频 | 久草视频免费在线播放 | 国产日韩精品在线观看 | 日本少妇久久久 | 成年人免费看av | 国产精品成人一区 | 国产精品露脸在线 | 欧美在线视频二区 | 丁香av在线 | 一区二区三区在线免费观看视频 | 日本中文字幕免费观看 | 国产999精品 | 91在线播放视频 | 亚洲视频2 | 亚洲男男gⅴgay双龙 | 色在线视频网 | 国产在线色 | 亚洲少妇激情 | 天天色天天操天天爽 | 日本黄色免费观看 | 国产精品毛片一区视频播 | 日韩在线视频免费播放 | 国产一区 在线播放 | 久草视频中文在线 | 日韩电影一区二区三区 | 911久久香蕉国产线看观看 | 国产精品资源在线 | 免费色av | 狠狠干免费| 婷婷在线不卡 | 国产大尺度视频 | 免费在线激情电影 | 韩国av电影网 | 免费黄色av.| 日韩精品免费一区二区 | av成人免费在线观看 | www.97视频| 精品久久久久国产免费第一页 | 午夜狠狠操 | 亚洲高清免费在线 | 国产精品婷婷 | 亚洲三级视频 | 一级一片免费看 | 中文亚洲欧美日韩 | 密桃av在线 | 黄色免费网站 | 免费大片av | 日韩在线观看视频一区二区三区 | 97涩涩视频 | 色多多视频在线 | 人人看黄色 | 福利区在线观看 | 久久精品3 | 日日夜夜狠狠 | 精品国偷自产国产一区 | 国产成人精品一区二三区 | 热久久精品在线 | 中文字幕第一页在线 | 色婷婷av在线 | 久久综合九色综合久久久精品综合 | 91黄色免费网站 | 国产小视频精品 | 中文字幕色综合网 | 精品国产一区二区三区日日嗨 | 九九国产精品视频 | 伊人五月在线 | 久久久久久久久福利 | 精品国产乱码久久久久久浪潮 | 国产日韩欧美在线免费观看 | av免费在线网 | 一区二区三区精品在线视频 | 美女网站视频一区 | 在线观看一级 | 五月婷婷黄色网 | 中文字幕在线免费 | 91九色最新 | 久久人人添人人爽添人人88v | 在线观看国产www | 国产欧美精品xxxx另类 | 国产亚洲视频在线免费观看 | 久久人人干| 中文字幕在线不卡国产视频 | 亚洲专区一二三 | 视频三区 | 91在线视频在线观看 | 亚洲专区在线播放 | 日韩精品不卡 | 国产亚洲精品久久久久久久久久久久 | 亚洲综合成人在线 | 国产黄色大片免费看 | 天天色中文 | 欧美日韩国产页 | 久草资源在线观看 | 中文字幕日韩免费视频 | 久久精品国产亚洲精品 | 欧美日本日韩aⅴ在线视频 插插插色综合 | 中文av日韩| 999色视频| 欧美日韩久久一区 | 久久视了| 婷婷电影在线观看 | 欧美吞精 | 黄色片网站av | 国产99久久久精品视频 | 99久久夜色精品国产亚洲 | 美女视频黄是免费的 | 91精品啪在线观看国产81旧版 | 色老板在线视频 | 在线观看一| 亚洲综合在线一区二区三区 | 一二三精品视频 | 国产成人精品久久久 | 国产成人在线观看免费 | 天天干天天操天天拍 | 久久精品国产久精国产 | 天天综合婷婷 | 日本精品久久 | 精品女同一区二区三区在线观看 | 国产第一福利 | 久久午夜剧场 | 国产色秀视频 | 欧美日韩视频在线观看免费 | 69精品人人人人 | av三级在线免费观看 | 欧美黑吊大战白妞欧美 | 成人日批视频 | 五月婷婷丁香激情 | 中文字幕永久在线 | www.888.av | 亚洲激情综合 | 国内视频在线观看 | 久久久这里有精品 | 91视频高清| 欧美精品久久久久久久亚洲调教 | 欧美 日韩 性 | 国产二区视频在线 | 亚洲国产视频在线 | 亚洲理论电影网 | 深夜国产在线 | 91精品综合在线观看 | 日韩在线二区 | 欧美色道 | 国产在线第三页 | 人人澡人人爽 | 久久久99国产精品免费 | 国产亚洲精品久久久久久久久久 | 9999国产精品 | 91av看片 | 黄色天堂在线观看 | 91精品国产综合久久婷婷香蕉 | 一区二区三区在线视频111 | 久久久久免费观看 | 日韩毛片一区 | av免费在线观看网站 | 亚洲精品在线一区二区三区 | 成人免费视频网站在线观看 | 狠狠色丁香久久婷婷综 | 国产亚洲视频中文字幕视频 | 一区二区在线影院 | 欧美色精品天天在线观看视频 | 日韩乱色精品一区二区 | 亚洲天天在线日亚洲洲精 | 久久久久 | 国产精品免费久久久久 | 国产高清不卡一区二区三区 | 色哟哟国产精品 | av电影不卡在线 | 99热在线观看免费 | 中文字幕网站视频在线 | 黄色小说免费在线观看 | 黄污视频网站大全 | 福利一区在线视频 | 日韩精品视频在线观看网址 | 久久艹在线观看 | 久久国产美女视频 | 成人在线播放网站 | 日韩视频中文字幕在线观看 | 日韩av一区二区在线影视 | 久久免费电影网 | 日韩色区 | 日韩在线一区二区免费 | 久久久99国产精品免费 | 国产在线播放一区二区 | 国产丝袜| 久久伦理影院 | 国产精品久久久久久久免费大片 | 午夜在线日韩 | 国产美女免费视频 | 国产精品21区 | 久久8| 欧美日韩在线免费观看视频 | 中文区中文字幕免费看 | 国产亚洲日本 | 国内精品二区 | 日日噜噜噜噜夜夜爽亚洲精品 | 国产精品福利av | 日韩a免费 | 日韩欧美视频在线观看免费 | 伊人干综合 | 中文字幕中文字幕在线中文字幕三区 | 免费99| 日本少妇久久久 | 韩国在线视频一区 | 亚洲视频h | 亚洲 欧美变态 另类 综合 | 美女免费网站 | 国产在线精品一区二区 | 在线看欧美 | 日本资源中文字幕在线 | 国产一级a毛片视频爆浆 | 国产在线观看免费观看 | 91精品久久久久久久久久入口 | 五月花婷婷 | 中文字幕在线影院 | 亚洲少妇自拍 | 综合久久2023 | 成人a免费看| 美女国产免费 | 最近中文字幕大全 | 麻豆精品国产传媒 | 97视频免费观看 | 激情综合网五月激情 | 一区二区理论片 | 亚洲午夜久久久影院 | 久久久久亚洲a | 久久久久久久久精 | 国产精品永久免费视频 | 日韩欧美一级二级 | 免费在线播放视频 | 亚洲第一成网站 | 久久综合九色综合久99 | 日韩有码中文字幕在线 | 最近久乱中文字幕 | 成人三级黄色 | 久久久久久国产精品免费 | 久久兔费看a级 | 久久99在线视频 | 黄色免费观看 | 精品美女国产在线 | 久久久精品二区 | 国产专区在线播放 | 欧美日韩国产免费视频 | 91成人免费看 | 日韩免费观看视频 | 九九99| 久久调教视频 | 青青河边草观看完整版高清 | 国产一级视屏 | 免费观看日韩av | 成人a视频在线观看 | 人人干狠狠操 | 国产在线播放一区 | 久热色超碰 | 成全免费观看视频 | 国产欧美日韩精品一区二区免费 | 中文字幕日本特黄aa毛片 | 日韩一级网站 | 久久伊人精品天天 | 特级毛片网 | 亚洲精品美女在线 | 91在线入口| 国产999精品久久久久久麻豆 | 中文字幕乱码亚洲精品一区 | 超级碰碰碰视频 | 国产精品一区二区三区99 | 九色精品免费永久在线 | 久久综合九色综合97_ 久久久 | 韩国av永久免费 | 国产免码va在线观看免费 | 国产精品久久一卡二卡 | 91中文视频 | 日韩精品久久久久久久电影竹菊 | 成人禁用看黄a在线 | 成人小视频在线观看免费 | 美女久久久久久久久久久 | 国产在线视频一区二区三区 | 91看片一区二区三区 | 91专区在线观看 | 欧美日本高清视频 | 久久久免费在线观看 | 亚洲伊人成综合网 | 成人性生交大片免费看中文网站 | 成年人三级网站 | 久久免费视频1 | 久久久久久高潮国产精品视 | 国产精品不卡 | 天天操操操操操 | 一区二区三区久久精品 | 在线免费观看黄色小说 | 在线观看视频免费大全 | 欧美一区二区日韩一区二区 | 国产精品久久久久久999 | 97国产在线视频 | 激情婷婷 | 中文字幕久久精品一区 | 麻花豆传媒一二三产区 | 国产综合在线观看视频 | 福利片视频区 | 亚洲精品久久久久久中文传媒 | 精品一区电影国产 | 久久视频免费在线观看 | 久久激情影院 | 久久精品官网 | 久久成人国产精品一区二区 | 99在线免费视频观看 | 国产免费嫩草影院 | 久久久久国产一区二区 | 久草在线免费新视频 | 四虎影视国产精品免费久久 | 婷婷丁香九月 | 丁香久久激情 | 日韩另类在线 | 久久综合九色综合久久久精品综合 | 日韩理论片中文字幕 | 久久在现 | 最新色站 | 在线色视频小说 | 成人黄色片免费 | 国产成人黄色片 | av片中文 | 精品欧美一区二区三区久久久 | 日韩com | 日日操天天操夜夜操 | 一区二区亚洲精品 | 天天玩夜夜操 | 新版资源中文在线观看 | 亚洲国产精品成人精品 | 狠狠干天天射 | 在线看的av网站 | 日本不卡视频 | av在线免费播放 | a√天堂资源 | 日韩超碰在线 | 日本精品久久久久久 | 九九综合九九综合 | 精品国自产在线观看 | 久久久免费在线观看 | av丝袜在线 | 日日日日 | 国产精品亚洲片夜色在线 | 日韩视频中文字幕 | 日韩在线一级 | 国产精品久久久久久69 | 亚洲天堂免费视频 | 在线免费观看黄色av | 国产精品久久久久久久久久久久 | 国产va在线 | 国产精选在线观看 | 日韩在线免费看 | 欧美亚洲精品一区 | 91色亚洲| av视屏在线播放 | 日韩精品视频免费专区在线播放 | 在线播放视频一区 | 欧美孕妇视频 | 99精品国产在热久久下载 | 国产网站色 | av观看在线观看 | 国产在线精品福利 | 亚洲国产97在线精品一区 | 日韩黄色免费看 | 久久伊人操| 亚洲人成人99网站 | 国产一级精品视频 | 国产精品专区一 | 免费av网址在线观看 | 99精品在线免费在线观看 | 成人亚洲精品久久久久 | 91成熟丰满女人少妇 | 中文字幕在线高清 | 91香蕉视频色版 | 国产二区免费视频 | 91在线免费观看网站 | 欧美日韩另类在线观看 | 亚洲 欧美 变态 国产 另类 | 蜜臀av免费一区二区三区 | 中文字幕国产精品一区二区 | 波多野结衣电影一区二区 | 久久精品一区二区三 | 国产玖玖在线 | 国产91精品欧美 | 91桃色免费视频 | 久久精品—区二区三区 | 欧美另类激情 | 国产资源 | 人人澡人人添人人爽一区二区 | 久久久精品综合 | 日本中文字幕久久 | 国产精品久久久久久久7电影 | 三级黄色大片在线观看 | 成人一级电影在线观看 | 黄色小说免费在线观看 | 九九热只有这里有精品 | 亚洲精品美女久久久 | 免费在线观看av网址 | 成人黄色在线观看视频 | 日韩超碰 | 亚洲另类交 | 国产美女被啪进深处喷白浆视频 | 91天堂影院 | 一级片视频免费观看 | 国产精品久久久久久久久免费看 | 国产99久久精品一区二区永久免费 | 日日日干 | 国内久久精品 | 免费午夜av| 国产精品免费观看在线 | 黄色视屏免费在线观看 | 久久久999精品视频 国产美女免费观看 | 96精品高清视频在线观看软件特色 | 免费av成人在线 | 一级黄色大片在线观看 | 免费在线观看国产精品 | 91在线免费看片 | 亚洲一区二区三区91 | 日韩欧美在线影院 | 亚洲精品456在线播放第一页 | 天天综合亚洲 | 欧美日韩成人 | 麻豆果冻剧传媒在线播放 | 人人干在线观看 | 九九热在线视频 | 天天操伊人 | 国产丝袜 | 久草国产在线观看 | 久草精品资源 | 国产黄色av影视 | 久久的色 | 免费亚洲黄色 | 色综合久久精品 | 在线播放精品一区二区三区 | 91亚洲网站 | 国产精久久久久久久 | 亚洲韩国一区二区三区 | 香蕉视频在线免费看 | 亚洲va天堂va欧美ⅴa在线 | 天天av综合网 | 麻豆久久一区二区 | 欧美日本不卡 | 一区二区三区 亚洲 | 综合精品在线 | 国产色婷婷 | 国产精品无av码在线观看 | 99婷婷狠狠成为人免费视频 | 91久久偷偷做嫩草影院 | 国产日韩欧美在线播放 | 99久久9 | 男女精品久久 | av网站在线观看播放 | 中文字幕日韩免费视频 | 国产亚洲精品久久久久5区 成人h电影在线观看 | 久久久久久美女 | 亚洲免费在线观看视频 | 碰碰影院 | 亚洲午夜久久久影院 | 99性视频 | www日日夜夜| 日韩av影视| 91精品办公室少妇高潮对白 | 亚洲精品午夜久久久久久久久久久 | 色婷婷97| 亚洲黄色片在线 | 国产成人亚洲在线观看 | 青草视频在线 | 国产一级一片免费播放放a 一区二区三区国产欧美 | av电影免费观看 | 日韩视频一二三区 | 视频在线一区 | 黄色成人在线观看 | 久久精品aaa| 色婷婷激情综合 | 成人av资源网站 | 国产理伦在线 | 夜夜操网 | 国产精品欧美精品 | 亚洲欧美乱综合图片区小说区 | 久久国产精品系列 | 欧洲亚洲女同hd | 日韩高清一区 | 精选久久 | 6080yy午夜一二三区久久 | 久久久久久久精 | 免费黄a大片 | 免费看国产视频 | a级片韩国 | 免费 在线 中文 日本 | 日韩精品一区二区免费视频 | 久久久久久久久久久久亚洲 | 国产一区二区在线免费观看 | 91香蕉国产在线观看软件 | 午夜精选视频 | 日本福利视频在线 | 波多野结衣久久精品 | 国产亚洲va综合人人澡精品 | 婷婷久久亚洲 | 国产专区在线播放 | 激情av一区二区 | 97在线观看免费观看高清 | 91亚洲国产成人久久精品网站 | 精品乱码一区二区三四区 | 97视频人人澡人人爽 | 国产成人精品一区二三区 | 91免费黄视频 | av三级在线播放 | 成人av地址| 欧美一级视频一区 | 精品久久久久久亚洲 | 开心色婷婷| 天堂成人在线 | 1区2区视频| 欧美一级片免费观看 | 久久一线| 粉嫩av一区二区三区入口 | 亚洲日韩欧美一区二区在线 | 国产精品国产三级国产专区53 | 日本黄色免费看 | 国产又粗又硬又长又爽的视频 | 国产精品永久在线 | 中文字幕免费成人 | 欧美激情另类文学 | 国产xvideos免费视频播放 | 日韩一区视频在线 | 91成人精品观看 | 精品毛片久久久久久 | 中文字幕a∨在线乱码免费看 | 狠狠干天天操 | 久操伊人 | 天操夜夜操 | 国产精品18毛片一区二区 | 欧洲成人av | 国模一二三区 | 国产亚洲婷婷免费 | 9999毛片| 亚洲理论电影 | 久久不见久久见免费影院 | 麻豆传媒视频在线免费观看 | 欧美成人亚洲成人 | 色综合在 | 国产欧美精品一区二区三区 | 97超碰国产在线 | 中文不卡视频 | 最近乱久中文字幕 | 99视频在线免费看 | 精品久久久久久久久久久久久久久久久久 | 日韩毛片在线播放 | 黄色av电影网 | 国产专区一 | 玖玖在线免费视频 | 国产欧美精品一区二区三区四区 | 69视频在线| 91成人在线看 | 国产资源在线播放 | 九九久久久 | 97在线观看 | 精品国产亚洲一区二区麻豆 | 808电影| 久久久精品亚洲 | 国产女人免费看a级丨片 | 中文字幕一区在线 | 国产精品久久在线 | 午夜影视剧场 | 99久视频 | 色丁香久久| 在线免费观看视频a | 区一区二区三区中文字幕 | 国产精品地址 | 久久综合九色综合97婷婷女人 | 在线观看视频国产 | 五月婷婷一级片 | 成人在线免费小视频 | 人人澡人 | 国产成人精品免费在线观看 | 久久久国产精品久久久 | 日韩精品中文字幕一区二区 | 亚洲黄色网络 | 97在线观看视频 | 国产伦精品一区二区三区… | 天天色天天操天天爽 | 在线观看完整版 | 婷婷亚洲五月色综合 | 欧美一级黄色网 | 日韩久久久久久久久久 | 一级a性色生活片久久毛片波多野 | 国产精品福利在线 | 日本在线观看视频一区 | 免费看一级黄色大全 | 日韩专区在线观看 | 亚洲天天看 | 亚洲午夜久久久久 | 国产精品永久 | 国产一区二区在线观看视频 | 国产区精品区 | 欧美成人黄色 | 国产一线二线三线性视频 | 在线观看久久久久久 | 亚洲欧美少妇 | 一级a毛片高清视频 | 天堂黄色片| 国产精品久久久久久模特 | 91片在线观看 | 欧洲黄色片 | 91黄色小视频 | 久久理论影院 | www.91国产 | 国产婷婷在线观看 | 国产一区电影在线观看 | 亚洲免费av一区二区 | 欧美精品做受xxx性少妇 | 天天爱天天操天天干 | 国产一区高清在线观看 | 国产精品夜夜夜一区二区三区尤 | 黄污网 | 欧美伦理电影一区二区 | 日韩午夜精品 | 久草免费在线视频 | 亚洲乱码在线观看 | 在线视频观看亚洲 | 国产精品毛片久久久久久久久久99999999 | 久久精品久久精品久久 | 国产91精品一区二区 | 欧美久久久影院 | 少妇激情久久 | 国产亚洲字幕 | 五月婷婷综| 欧美精品一二 | 韩国av一区 | 精品久久美女 | 国产免费xvideos视频入口 | 久久亚洲国产精品 | 精品一区欧美 | 久久久久一区二区三区四区 | 最新av在线播放 | 中文字幕在线观看视频免费 | 国产视频精品免费播放 | 97精品国自产拍在线观看 | 午夜10000| 97电影在线观看 | 国产 一区二区三区 在线 | 4438全国亚洲精品观看视频 | 国产日韩精品一区二区在线观看播放 | 欧美成人猛片 | 中文字幕在线一区二区三区 | 91亚洲精 | 涩涩网站在线看 | 东方av在线免费观看 | 日日干 天天干 | 97天堂| 亚洲精品字幕在线观看 | 精品国产伦一区二区三区免费 | av片中文 | 超碰97国产精品人人cao | 国产色拍拍拍拍在线精品 | 在线国产一区二区三区 | 在线亚洲日本 | 午夜美女福利直播 | 欧美精品午夜 | 婷婷精品在线视频 | 亚洲精品欧美视频 | 中文字幕在线播放一区 | 国产高清视频色在线www | 色偷偷中文字幕 | 最近中文字幕高清字幕在线视频 | 国产xvideos免费视频播放 | 日韩在线一二三区 | 婷婷激情网站 | 97精品超碰一区二区三区 | 精品久久电影 | 日韩中文字幕在线 | 五月婷婷另类国产 | 成人一级电影在线观看 | 亚洲三级影院 | 久久精品国产免费 | 欧美日韩视频观看 | 97人人添人澡人人爽超碰动图 | 久久久91精品国产 | 嫩草伊人久久精品少妇av | 久久久久久国产精品美女 | 欧美综合色在线图区 | 97成人精品区在线播放 | 久久久久久久久国产 | 九九热久久久 | 丁香激情网| 精品91在线| 88av色| 国产高清视频网 | 一级做a视频 | 国产亚洲精品久久久久久 | 国产亚洲情侣一区二区无 | 成人黄性视频 | 国产一区网址 | 91精品国产一区二区三区 | 亚洲乱码一区 | 日韩激情免费视频 | 国产一级精品绿帽视频 | 亚洲一区二区视频在线 | 欧美少妇xxxxxx | 天天操天天干天天玩 | 干综合网 | 精品欧美一区二区精品久久 | 中文字幕人成乱码在线观看 | 福利一区在线视频 | 狠狠色伊人亚洲综合网站野外 | 色综合综合 | 久草在线视频首页 | 欧美污在线观看 | 精品国产乱子伦一区二区 | 欧美一级小视频 | 免费影视大全推荐 | 亚洲另类视频在线观看 | 免费三级黄色片 | 久久视频一区 | bbw av| 精品免费久久久久久 | 热re99久久精品国产99热 | 麻花豆传媒mv在线观看网站 | 四虎成人精品永久免费av九九 | 九色porny真实丨国产18 | www激情久久| 国产又粗又猛又黄视频 | 夜色资源站国产www在线视频 | 亚洲最大av网站 | 男女激情免费网站 | 一级片免费视频 | 黄色av成人在线观看 | 色播亚洲婷婷 | 亚洲精品999 | 国产一级一级国产 | 婷婷亚洲激情 | 亚洲精品午夜视频 | 狠狠做深爱婷婷综合一区 | 日b视频在线观看网址 | 亚洲国内精品视频 | 日本久久久久久久久久 | 四虎在线观看精品视频 | 最近中文字幕大全中文字幕免费 | 97国产超碰 | 欧美成人va| 亚洲不卡在线 | 国产123av| 日韩午夜网站 | 特级xxxxx欧美| 美女免费网视频 | 久久成人国产精品一区二区 | 992tv在线观看| 日b视频国产 | 特级西西人体444是什么意思 | 在线观看的av网站 | 久久久麻豆精品一区二区 | 成人性生爱a∨ | 亚洲在线高清 | 美女精品久久久 | 成人国产精品久久久久久亚洲 | 亚洲精品欧洲精品 | 色综合婷婷 | 一级黄色免费网站 | 三级av在线 | 久黄色| 亚洲高清精品在线 | 亚洲精品字幕在线 | 日韩三级.com | 久久久久99999| 香蕉视频免费在线播放 | a级一a一级在线观看 | 狠狠躁日日躁狂躁夜夜躁av | 午夜久久久久 | 在线视频你懂得 | 91免费网站在线观看 | 国产免费又爽又刺激在线观看 | 日韩欧美视频在线播放 | 手机版av在线 | 中文字幕在线资源 | wwwav视频| 国产直播av| 国产 欧美 日产久久 | 成年人视频在线免费播放 | 久久精品99国产国产 | 久久一本综合 | 亚洲天天草 | 亚洲闷骚少妇在线观看网站 | 久草免费在线视频观看 | 日韩大片在线免费观看 | 欧美精品久久久久a | 久久天| 亚洲最新av网站 | 日韩在线网 | 91福利视频免费观看 | www激情com | 97影视| 婷婷av网| 国产中文字幕视频在线观看 | 99热在线这里只有精品 | 亚洲免费国产 | 五月天六月婷婷 | 久久精品在线免费观看 | 亚洲视频免费在线观看 | 国产理论一区二区三区 | 久久夜靖品 | 国产麻豆剧果冻传媒视频播放量 | 婷婷精品视频 | 欧美日韩免费在线视频 | 亚洲精品视| 国产香蕉97碰碰久久人人 | 日韩xxxbbb | 激情欧美国产 | 久久黄色片子 | 天堂在线视频中文网 | 成人h在线 | 欧美一区二区三区在线视频观看 | 国产一区视频在线播放 | 亚洲欧美日韩国产一区二区 | 99免费在线播放99久久免费 | 999视频在线播放 | 久久久久色 | 人人狠狠综合久久亚洲婷 | 日韩免费一区二区在线观看 | 欧美最猛性xxxxx(亚洲精品) | 一区二区三区在线免费 | 中国一级片在线观看 | 亚洲国产精品一区二区久久hs | 手机成人av | jizz欧美性9| 在线观看国产福利片 | 在线天堂中文在线资源网 | 欧美伊人网 | 日韩av电影国产 | 97在线超碰| 日日射av | 色婷婷视频网 | 婷婷六月激情 | 亚洲国产日韩一区 | 国产特级毛片aaaaaa毛片 | 久久草精品 | 欧美久草网 | 欧美三人交 | 精品女同一区二区三区在线观看 | 91精品免费 | www免费 | 久久伊99综合婷婷久久伊 | 综合激情婷婷 | 一区二区三区在线免费观看视频 | 91理论片午午伦夜理片久久 | 久久精品免视看 | 久久精品人人做人人综合老师 | 久久久毛片 | 黄色在线看网站 | 国产精品成人av久久 | 一区二区视频免费在线观看 | 91日韩免费| 国产乱码精品一区二区三区介绍 | 韩日精品中文字幕 | 欧美精品久久久久久久久久丰满 | 亚洲va韩国va欧美va精四季 | 精品久久视频 | 日本激情视频中文字幕 | 日韩视频免费观看高清 | 久久久国产精品一区二区三区 | 美女黄频 | 国产精品门事件 | 伊人久久电影网 | 久久综合狠狠综合久久狠狠色综合 |