2020/8/24
英语四级一篇
学习李超线段树
四题:
#include"stdio.h" #include"string.h" #include"stack" #include"map" #include"math.h" #include"iostream" #include"vector" #include"queue" #include"algorithm" using namespace std; typedef pair<int,int> PII; inline int read(){ int s = 0, w = 1; char ch = getchar(); while(ch < '0' || ch > '9') { if(ch == '-') w = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { s = (s << 3) + (s << 1) + (ch ^ 48); ch = getchar(); } return s * w; } const int N = 300100; char str[210][210]; struct House{ int x,y; }hou[N]; struct People{ int x,y; }peo[N]; int t1,t2; int n,m; int G[210][210]; int la[N],lb[N]; int va[N],vb[N]; int match[N],ans[N]; int delta; int get_dist(int x1,int y1,int x2,int y2){ int s = abs(x1 - x2) + abs(y1 - y2); return s; } bool dfs(int x){ va[x] = 1; for(int y = 1; y <= n; y ++){ if(!vb[y]){ if(abs(la[x] + lb[y] - G[x][y]) == 0){ vb[y] = 1; if(!match[y] || dfs(match[y])){ match[y] = x; return true; } } else delta = min(delta,la[x] + lb[y] - G[x][y]); } } return false; } int KM(){ for(int i = 1; i <= n;i ++){ la[i] = -(1 << 30); lb[i] = 0; for(int j = 1; j <= n; j ++) la[i] = max(la[i],G[i][j]); } for(int i = 1; i <= n; i ++) while(true){ memset(va,0,sizeof(va)); memset(vb,0,sizeof(vb)); delta = 1 << 30; if(dfs(i)) break; for(int j = 1; j <= n; j ++){ if(va[j]) la[j] -= delta; if(vb[j]) lb[j] += delta; } } } int main(){ while(~scanf("%d%d",&n,&m)){ if(n == 0) break; t1 = t2 = 0; memset(G,0,sizeof(G)); memset(ans,0,sizeof(ans)); memset(match,0,sizeof(match)); memset(la,0,sizeof(la)); memset(lb,0,sizeof(lb)); for(int i = 1; i <= n; i ++){ scanf("%s",str[i] + 1); } for(int i = 1; i <= n; i ++){ for(int j = 1; j <= m; j ++){ if(str[i][j] == '.') continue; if(str[i][j] == 'm') { peo[++ t2].x = i; peo[t2].y = j; } else { hou[++ t1].x = i; hou[t1].y = j; } } } for(int i = 1; i <= t2 ;i ++){ for(int j = 1; j <= t1; j ++){ int w = get_dist(peo[i].x,peo[i].y,hou[j].x,hou[j].y); G[i][j] = -w; } } n = t1; KM(); int sum = 0; for(int i = 1;i <= n; i ++){ sum -= G[match[i]][i]; } printf("%d\n",sum); } } /* 3 1 2 3 2 2 6 */ #include"stdio.h" #include"string.h" #include"stack" #include"map" #include"math.h" #include"iostream" #include"vector" #include"queue" #include"algorithm" using namespace std; #define OK printf("\n"); #define Debug printf("this_ok\n"); #define INF 1e18 typedef long long ll; #define scanll(a,b) scanf("%lld%lld",&a,&b); #define scanl(a) scanf("%lld",&a); #define printl(a,b) if(b == 0) printf("%lld ",a); else printf("%lld\n",a); #define print_int(a,b) if(b == 0) printf("%d ",a); else printf("%d\n",a); typedef pair<int,int> PII; inline int read(){ int s = 0, w = 1; char ch = getchar(); while(ch < '0' || ch > '9') { if(ch == '-') w = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { s = (s << 3) + (s << 1) + (ch ^ 48); ch = getchar(); } return s * w; } const ll mod = 998244353; const int N = 50010,M = 300010; const double pi = acos(-1); const int inf = 1 << 29; int n,m,t,s,tot; ll maxflow; int head[N],ver[M],Next[M],edge[M],d[N]; queue<int> q; void add(int x,int y,int z){ ver[++ tot] = y; Next[tot] = head[x]; edge[tot] = z; head[x] = tot; ver[++ tot] = x; edge[tot] = 0; Next[tot] = head[y]; head[y] = tot; } bool bfs(){ memset(d,0,sizeof(d)); while(q.size())q.pop(); q.push(s); d[s] = 1; while(q.size()){ int x = q.front(); q.pop(); for(int i = head[x]; i; i = Next[i]) if(edge[i] && !d[ver[i]]){ q.push(ver[i]); d[ver[i]] = d[x] + 1; if(ver[i] == t) return 1; } } return 0; } int dinic(int x,ll flow){ if(x == t) return flow; ll rest = flow,k; for(int i = head[x]; i && rest; i = Next[i]){ if(edge[i] && d[ver[i]] == d[x] + 1){ k = dinic(ver[i],min(rest,(ll)edge[i])); if(!k) d[ver[i]] = 0; edge[i] -= k; edge[i ^ 1] += k; rest -= k; } } return flow - rest; } int main(){ n = read(),m = read();s = 1; t = m; tot = 1; for(int i = 1; i <= n; i ++){ int x = read(),y = read();int c = read(); add(x,y,c); } ll flow = 0; while(bfs()) while(flow = dinic(s,inf)) maxflow += flow; printf("%lld\n",maxflow); } /* 3 1 2 3 2 2 6 */ #include"stdio.h" #include"string.h" #include"stack" #include"queue" #include"algorithm" using namespace std; #define OK printf("\n"); #define De_bug printf("this_ok\n"); typedef long long ll; #define scanll(a,b) scanf("%lld%lld",&a,&b); #define scanl(a) scanf("%lld",&a); #define printl(a) printf("%lld",a); #define print_int(a) printf("%d ",a); inline int read(){ int s = 0, w = 1; char ch = getchar(); while(ch < '0' || ch > '9') { if(ch == '-') w = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { s = (s << 3) + (s << 1) + (ch ^ 48); ch = getchar(); } return s * w; } const int SIZE = 100010; struct Treap{ int l,r; int val,dat; int cnt,Size; }a[SIZE]; int tot,root,n,INF = 0x7fffffff; int New(int val){ a[++ tot].val = val; a[tot].dat = rand(); a[tot].cnt = a[tot].Size = 1; return tot; } void Update(int p){ a[p].Size = a[a[p].l].Size + a[a[p].r].Size + a[p].cnt; } void Build(){ New(-INF),New(INF); root = 1;a[1].r = 2; Update(root); } int GetRankByVal(int p,int val){ if(p == 0) return 0; if(val == a[p].val) return a[a[p].l].Size + 1; if(val < a[p].val) return GetRankByVal(a[p].l,val); return GetRankByVal(a[p].r,val) + a[a[p].l].Size + a[p].cnt; } int GetRankByRank(int p,int Rank){ if(p == 0) return INF; if(a[a[p].l].Size >= Rank) return GetRankByRank(a[p].l,Rank); if(a[a[p].l].Size + a[p].cnt >= Rank) return a[p].val; return GetRankByRank(a[p].r,Rank - a[a[p].l].Size - a[p].cnt); } void Zig(int &p){ int q = a[p].l; a[p].l = a[q].r; a[q].r = p; p = q; Update(a[p].r); Update(p); } void Zag(int &p){ int q = a[p].r; a[p].r = a[q].l; a[q].l = p; p = q; Update(a[p].l); Update(p); } void Insert(int &p,int val){ if(p == 0) { p = New(val); return ; } if(val == a[p].val){ a[p].cnt ++; Update(p); return ; } if(val < a[p].val){ Insert(a[p].l,val); if(a[p].dat < a[a[p].l].dat) Zig(p); } else { Insert(a[p].r,val); if(a[p].dat < a[a[p].r].dat) Zag(p); } Update(p); } int GetPre(int val){ int ans = 1; int p = root; while(p){ if(val == a[p].val){ if(a[p].l > 0){ p = a[p].l; while(a[p].r > 0) p = a[p].r; ans = p; } break; } if(a[p].val < val && a[p].val > a[ans].val) ans = p; p = val < a[p].val ? a[p].l : a[p].r; } return a[ans].val; } int GetNext(int val){ int ans = 2; int p = root; while(p){ if(val == a[p].val){ if(a[p].r > 0){ p = a[p].r; while(a[p].l > 0) p = a[p].l; ans = p; } break; } if(a[p].val > val && a[p].val < a[ans].val) ans = p; p = val < a[p].val ? a[p].l : a[p].r; } return a[ans].val; } void Remove(int &p,int val){ if(p == 0) return ; if(val == a[p].val) { if(a[p].cnt > 1) { a[p].cnt --; Update(p); return ; } if(a[p].l || a[p].r){ if(a[p].r == 0 || a[a[p].l].dat > a[a[p].r].dat) Zig(p),Remove(a[p].r,val); else Zag(p),Remove(a[p].l,val); Update(p); } else p = 0; return ; } val < a[p].val ? Remove(a[p].l,val) : Remove(a[p].r,val); Update(p); } int main(){ Build(); n = read(); while(n --){ int opt,x; opt = read(); x = read(); switch(opt){ case 1 : Insert(root,x);break; case 2 : Remove(root,x);break; case 3 : printf("%d\n",GetRankByVal(root,x) - 1);break; case 4 : printf("%d\n",GetRankByRank(root,x + 1));break; case 5 : printf("%d\n",GetPre(x)); break; case 6 : printf("%d\n",GetNext(x)); break; } } } #include"stdio.h" #include"string.h" #include"stack" #include"map" #include"math.h" #include"iostream" #include"vector" #include"queue" #include"algorithm" using namespace std; #define OK printf("\n"); #define Debug printf("this_ok\n"); #define inf 1e9 #define INF 1e18 typedef long long ll; #define scanll(a,b) scanf("%lld%lld",&a,&b); #define scanl(a) scanf("%lld",&a); #define printl(a,b) if(b == 0) printf("%lld ",a); else printf("%lld\n",a); #define print_int(a,b) if(b == 0) printf("%d ",a); else printf("%d\n",a); typedef pair<int,int> PII; inline int read(){ int s = 0, w = 1; char ch = getchar(); while(ch < '0' || ch > '9') { if(ch == '-') w = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { s = (s << 3) + (s << 1) + (ch ^ 48); ch = getchar(); } return s * w; } const ll mod = 998244353; const int N = 600000; const double pi = acos(-1); int n, m, block; int a[N], belong[N], f[N], tot,top; int d[1000][1000]; vector<int> g[N]; int cnt[N]; int Query(int l, int r, int val){ int t = upper_bound(g[val].begin(), g[val].end(), r)- lower_bound(g[val].begin(), g[val].end(), l); return t; } void pre(int x){ memset(cnt, 0, sizeof(cnt)); int maxx = -1, ans = 0; for (int i = (x - 1)*block + 1; i <= n; i++){ cnt[a[i]]++; if (cnt[a[i]] > maxx || (cnt[a[i]] == maxx&&a[i] < ans)){ ans = a[i]; maxx = cnt[a[i]]; } d[x][belong[i]] = ans; } } int query(int l, int r){ int ans = d[belong[l] + 1][belong[r] - 1]; int mx = Query(l, r, ans); int cnt = 0; int up = min(r, belong[l] * block); for (int i = l; i <= up; i++){ cnt = Query(l, r, a[i]); if (cnt > mx || (cnt == mx&&f[ans] > f[a[i]])){ mx = cnt; ans = a[i]; } } if(belong[l] == belong[r]) return ans; for (int i = (belong[r] - 1)*block + 1; i <= r; i++){ cnt = Query(l, r, a[i]); if (cnt > mx || (cnt == mx&&ans > a[i])){ mx = cnt; ans = a[i]; } } return ans; } int main() { n = read(); m = read(); for (int i = 1; i <= n; i++){ scanf("%d", &a[i]); f[++ top] = a[i]; } block=max(1,(int)(n/sqrt(m*log2(n)))); for (int i = 1; i <= n; i++) belong[i] = (i - 1) / block + 1; sort(f + 1, f + n + 1); top = unique(f + 1, f + n + 1) - f-1; for (int i = 1; i <= n; i++){ a[i] = lower_bound(f + 1, f + top + 1, a[i]) - f; g[a[i]].push_back(i); } int ans = 0; for (int i = 1; i <= belong[n]; i++) pre(i); while (m--){ int l = read(), r = read(); l = (l + ans - 1) % n + 1; r = (r + ans - 1) % n + 1; if (l>r) swap(l, r); ans = f[query(l, r)]; printf("%d\n", ans); } return 0; }