# 2017中国大学生程序设计竞赛-哈尔滨站

## Contest Info

Solved A B C D E F G H I J K L M
8 / 13 O O - Ø - O - O - - Ø Ø Ø
• O 在比赛中通过
• Ø 赛后通过
• ! 尝试了但是失败了
• - 没有尝试

## Solutions

### A - Palindrome

Code
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef double db;
typedef long double ld;
const int MAXN = 5e5 + 5, MAXM = 4e5 + 5, BOUND = 2e5, MOD = 1e9+7, INF = 0x3f3f3f3f, base = 10000;
const int inv2 = (MOD + 1) >> 1;
const ll INFL = 0x3f3f3f3f3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-9;
#define lson o<<1,l,m
#define rson o<<1|1,m+1,r
#define lc(x) ch[x][0]
#define pii pair<int,int>
#define vi vector<int>
#define vii vector<pair<int,int>>
#define rc(x) ch[x][1]
#define random(a,b) ((a)+rand()%((b)-(a)+1))
#define all(a) (a).begin(), (a).end()
#define sz(a) int(a.size())
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define fi first
#define se second
#define MP std::make_pair
#define ri register int
//#define sz(a) int((a).size())
inline int add(int a, int b) {return a + b >= MOD ? a + b - MOD : a + b;}
inline int dec(int a, int b) {return a < b ? a - b + MOD : a - b;}
inline int mul(int a, int b) {return 1ll * a * b % MOD;}
template <typename T>
inline void cmin(T &a,T b){a = min(a,b);}
template <typename T>
inline void cmax(T &a,T b){a = max(a,b);}
ll qpow(ll a,ll b){
ll ans=1;
for(;b;b>>=1,a=a*a%MOD)if(b&1)ans=ans*a%MOD;
return ans;
}
mt19937 mrand(random_device{}());
char s[MAXN*2],t[MAXN];
int p[MAXN*2],n;
void manacher(){
s[0]=s[1]='#';
for(int i=1;i<=n;i++){
s[i*2] = t[i];
s[i*2+1]='#';
}
int _n=n*2+1;
int m,mx=0;
for(int i=_n+1;!s[i];i++)s[i]='0';
for(int i=1;i<=_n;i++){
if(mx>i)p[i]=min(p[2*m-i],p[m]+m-i);
else p[i]=1;
for(;s[i+p[i]]==s[i-p[i]];++p[i]);
if(p[i]+i>mx)mx=p[i]+i,m=i;
}
}
int bit[MAXN];
void upd(int x,int v){
for(;x;x-=x&-x)bit[x]+=v;
}
int que(int x){
int ans=0;
for(;x<=n;x+=x&-x)ans += bit[x];
return ans;
}

priority_queue<pii> q;
void run(){
cin>>(t+1);
n=strlen(t+1);
rep(i,0,n)bit[i]=0;
while(!q.empty())q.pop();
manacher();
ll ans=0;
rep(i,1,n){
while(!q.empty() && -(q.top().fi)<i)upd(q.top().se,-1),q.pop();
ans += que(i-p[i*2]/2+1);
upd(i,1);
q.push({-(i+p[i*2]/2-1),i});
}
cout<<ans<<'\n';
}
int main() {
ios::sync_with_stdio(false); cin.tie(0);
int _;cin>>_;
while(_--)run();
return 0;
}


### B - K-th Number

Code
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef double db;
typedef long double ld;
const int MAXN = 1e5 + 5, MAXM = 4e5 + 5, BOUND = 2e5, MOD = 1e9+7, INF = 0x3f3f3f3f, base = 10000;
const int inv2 = (MOD + 1) >> 1;
const ll INFL = 0x3f3f3f3f3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-9;
#define lson o<<1,l,m
#define rson o<<1|1,m+1,r
#define lc(x) ch[x][0]
#define pii pair<int,int>
#define vi vector<int>
#define vii vector<pair<int,int>>
#define rc(x) ch[x][1]
#define random(a,b) ((a)+rand()%((b)-(a)+1))
#define all(a) (a).begin(), (a).end()
#define sz(a) int(a.size())
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define fi first
#define se second
#define MP std::make_pair
#define ri register int
//#define sz(a) int((a).size())
inline int add(int a, int b) {return a + b >= MOD ? a + b - MOD : a + b;}
inline int dec(int a, int b) {return a < b ? a - b + MOD : a - b;}
inline int mul(int a, int b) {return 1ll * a * b % MOD;}
template <typename T>
inline void cmin(T &a,T b){a = min(a,b);}
template <typename T>
inline void cmax(T &a,T b){a = max(a,b);}
ll qpow(ll a,ll b){
ll ans=1;
for(;b;b>>=1,a=a*a%MOD)if(b&1)ans=ans*a%MOD;
return ans;
}
mt19937 mrand(random_device{}());
int n,k,a[MAXN];
ll M;
bool check(int x){
int sum=0;
ll cnt=0;
for(int l=1,r=0;l<=n;sum-=(a[l++]>=x)){
while(r+1<=n && sum<k)sum+=(a[++r]>=x);
if(sum>=k)cnt += n-r+1;
}
return cnt>=M;
}
void run(){
cin>>n>>k>>M;
rep(i,1,n)cin>>a[i];

int l=1,r=1e9,m;
while(l<r){
m = (l+r+1)/2;
if(check(m))l = m;
else r=m-1;
}
cout<<l<<'\n';
}
int main() {
ios::sync_with_stdio(false); cin.tie(0);
int _;cin>>_;
while(_--)run();
return 0;
}


### D - X-Men

Code
/*
* Author:  heyuhhh
* Created Time:  2020/6/16 15:45:05
*/
#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <vector>
#include <cmath>
#include <set>
#include <map>
#include <queue>
#include <iomanip>
#include <assert.h>
#include <functional>
#include <numeric>
#define MP make_pair
#define fi first
#define se second
#define pb push_back
#define sz(x) (int)(x).size()
#define all(x) (x).begin(), (x).end()
#define INF 0x3f3f3f3f
#define Local
#ifdef Local
#define dbg(args...) do { cout << #args << " -> "; err(args); } while (0)
void err() { std::cout << std::endl; }
template<typename T, typename...Args>
void err(T a, Args...args) { std::cout << a << ' '; err(args...); }
template <template<typename...> class T, typename t, typename... A>
void err(const T <t> &arg, const A&... args) {
for (auto &v : arg) std::cout << v << ' '; err(args...); }
#else
#define dbg(...)
#endif
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
const int N = 1e3 + 5;

int n, m;
vector <int> G[N];
int a[N];

int Max, rt;
void dfs(int u, int fa, int d) {
if (a[u]) {
if (d > Max) {
Max = d;
rt = u;
}
}
for (auto v : G[u]) if (v != fa) {
dfs(v, u, d + 1);
}
}

void run() {
cin >> n >> m;
for (int i = 1; i <= n; i++) {
a[i] = 0;
G[i].clear();
}
for (int i = 1; i <= m; i++) {
int x; cin >> x;
a[x] = 1;
}
for (int i = 1; i < n; i++) {
int u, v; cin >> u >> v;
G[u].push_back(v);
G[v].push_back(u);
}
Max = 0;
for (int i = 1; i <= n; i++) {
if (a[i]) {
dfs(i, 0, 0);
Max = 0;
dfs(rt, 0, 0);
break;
}
}
cout << (double)(Max / 2) << '\n';
}

int main() {
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
cout << fixed << setprecision(2);
int T; cin >> T; while(T--)
run();
return 0;
}


### F - Permutation

Code
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef double db;
typedef long double ld;
const int MAXN = 1e5 + 5, MAXM = 4e5 + 5, BOUND = 2e5, MOD = 1e9+7, INF = 0x3f3f3f3f, base = 10000;
const int inv2 = (MOD + 1) >> 1;
const ll INFL = 0x3f3f3f3f3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-9;
#define lson o<<1,l,m
#define rson o<<1|1,m+1,r
#define lc(x) ch[x][0]
#define pii pair<int,int>
#define vi vector<int>
#define vii vector<pair<int,int>>
#define rc(x) ch[x][1]
#define random(a,b) ((a)+rand()%((b)-(a)+1))
#define all(a) (a).begin(), (a).end()
#define sz(a) int(a.size())
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define fi first
#define se second
#define MP std::make_pair
#define ri register int
//#define sz(a) int((a).size())
const int N = 2e5,M = (1<<20);
inline int add(int a, int b) {return a + b >= MOD ? a + b - MOD : a + b;}
inline int dec(int a, int b) {return a < b ? a - b + MOD : a - b;}
inline int mul(int a, int b) {return 1ll * a * b % MOD;}
template <typename T>
inline void cmin(T &a,T b){a = min(a,b);}
template <typename T>
inline void cmax(T &a,T b){a = max(a,b);}
ll qpow(ll a,ll b){
ll ans=1;
for(;b;b>>=1,a=a*a%MOD)if(b&1)ans=ans*a%MOD;
return ans;
}
mt19937 mrand(random_device{}());
int ans[MAXN];
void run(){
int n;cin>>n;
rep(i,1,(n+1)/2){
ans[i*2-1] = i;
}
int j=1;
rep(i,(n+1)/2+1,n){
ans[j*2] = i;
j++;
}
rep(i,1,n)cout<<ans[i]<<" \n"[i==n];
}
int main() {
ios::sync_with_stdio(false); cin.tie(0);
int _;cin>>_;
while(_--)run();
return 0;
}


### H - A Simple Stone Game

$$n$$堆石子，每堆$$a_i$$个石头，每次操作可以移动一个石头从一堆到另外一堆。现在使得所有石堆石子个数都为某个$$x$$的倍数，问最少移动多少次。

Code
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef double db;
typedef long double ld;
const int MAXN = 1e5 + 5, MAXM = 4e5 + 5, BOUND = 2e5, MOD = 1e9+7, INF = 0x3f3f3f3f, base = 10000;
const int inv2 = (MOD + 1) >> 1;
const ll INFL = 0x3f3f3f3f3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-9;
#define lson o<<1,l,m
#define rson o<<1|1,m+1,r
#define lc(x) ch[x][0]
#define pii pair<int,int>
#define vi vector<int>
#define vii vector<pair<int,int>>
#define rc(x) ch[x][1]
#define random(a,b) ((a)+rand()%((b)-(a)+1))
#define all(a) (a).begin(), (a).end()
#define sz(a) int(a.size())
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define fi first
#define se second
#define MP std::make_pair
#define ri register int
//#define sz(a) int((a).size())
inline int add(int a, int b) {return a + b >= MOD ? a + b - MOD : a + b;}
inline int dec(int a, int b) {return a < b ? a - b + MOD : a - b;}
inline int mul(int a, int b) {return 1ll * a * b % MOD;}
template <typename T>
inline void cmin(T &a,T b){a = min(a,b);}
template <typename T>
inline void cmax(T &a,T b){a = max(a,b);}
ll qpow(ll a,ll b){
ll ans=1;
for(;b;b>>=1,a=a*a%MOD)if(b&1)ans=ans*a%MOD;
return ans;
}
mt19937 mrand(random_device{}());
int primes[MAXN],cnt;
bool is_prime[MAXN];
void init(){
is_prime[1] = 1;
for(int i=2;i<=100000;i++){
if(!is_prime[i])primes[cnt++]=i;
for(int j=0;j<cnt&&primes[j]*i<=100000;j++){
is_prime[i*primes[j]]=1;
if(i%primes[j]==0)break;
}
}
}
int a[MAXN];
priority_queue<int,vi,greater<int>> q;
void run(){
int n;cin>>n;
ll sum=0;
rep(i,1,n)cin>>a[i],sum+=a[i];
ll ans=INFL;
for(ll i=2;i<=sqrt(sum+0.5);i++){
if(sum%i==0){
while(sum%i==0){
sum/=i;
}
ll sum2=0;
rep(j,1,n){
sum2 += a[j]%i;
}
int cnt = sum2/i;
rep(j,1,n){
if(a[j]%i)q.push(a[j]%i);
if(int(q.size())>cnt)q.pop();
}
while(!q.empty()){
int t=q.top();q.pop();
sum2-=t;
}
ans = min(ans,sum2);
}
}
if(sum>1){
ll sum2=0;
rep(j,1,n){
sum2 += a[j]%sum;
}
int cnt = sum2/sum;
rep(j,1,n){
if(a[j]%sum)q.push(a[j]%sum);
if(int(q.size())>cnt)q.pop();
}
while(!q.empty()){
int t=q.top();q.pop();
sum2-=t;
}
ans = min(ans,sum2);
}
cout<<ans<<'\n';
}
int main() {
ios::sync_with_stdio(false); cin.tie(0);
int _;cin>>_;
while(_--)run();
return 0;
}


### K - Server

Code
/*
* Author:  heyuhhh
* Created Time:  2020/6/15 16:24:12
*/
#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <vector>
#include <cmath>
#include <set>
#include <map>
#include <queue>
#include <iomanip>
#include <assert.h>
#include <functional>
#include <numeric>
#define MP make_pair
#define fi first
#define se second
#define pb push_back
#define sz(x) (int)(x).size()
#define all(x) (x).begin(), (x).end()
#define INF 0x3f3f3f3f
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
const int N = 1e5 + 5;

int n, t;
int a[N], b[N];
vector <pii> v[N];

ll c[N];

struct BIT {
ll c[N];
int lowbit(int x) {
return x & -x;
}
void update(int x, ll v) {
++x;
x = t + 1 - x + 1;
for (; x <= t + 1; x += lowbit(x)) {
c[x] = min(c[x], v);
}
}
ll query(int x) {
++x;
x = t + 1 - x + 1;
ll res = 1e18;
for (; x; x -= lowbit(x)) {
res = min(res, c[x]);
}
return res;
}
}bit;

ll check(int x) {
ll res = 0;
for (int i = 1; i <= n; i++) {
c[i] = a[i] - 1ll * b[i] * x;
}
for (int i = 0; i <= t + 1; i++) {
bit.c[i] = 1e18;
}
bit.update(0, 0);
for (int i = 1; i <= t; i++) {
for (auto it : v[i]) {
int l = it.fi, r = i, id = it.se;
ll now = bit.query(l - 1);
if (c[id] < 0) res -= c[id], c[id] = 0;
bit.update(i, now + c[id]);
}
}
return bit.query(t) <= res;
}

void run() {
scanf("%d%d", &n, &t);
for (int i = 0; i <= t; i++) {
v[t].clear();
}
for (int i = 1; i <= n; i++) {
int l, r; scanf("%d%d", &l, &r);
v[r].emplace_back(MP(l, i));
scanf("%d%d", &a[i], &b[i]);
a[i] *= 10000;
}
int l = 0, r = 1e7 + 5, mid;
while (l < r) {
mid = (l + r) >> 1;
if (check(mid)) {
r = mid;
} else {
l = mid + 1;
}
}
double ans = 1.0 * r / 10000;
printf("%.3f\n", ans);
}

int main() {
int T; scanf("%d", &T); while(T--)
run();
return 0;
}


### L - Color a Tree

$$A+B,A,B\leq 10^5$$个限制，其中$$A$$个限制为每个点子树内至少有多少个染色点，$$B$$个限制为每个点子树外至少有多少个点。

ok，这两点想通了这个题就很简单了，直接树$$dp$$来check一下就行。

Code
/*
* Author:  heyuhhh
* Created Time:  2020/6/16 9:21:10
*/
#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <vector>
#include <cmath>
#include <set>
#include <map>
#include <queue>
#include <iomanip>
#include <assert.h>
#include <functional>
#include <numeric>
#define MP make_pair
#define fi first
#define se second
#define pb push_back
#define sz(x) (int)(x).size()
#define all(x) (x).begin(), (x).end()
#define INF 0x3f3f3f3f
#define Local
#ifdef Local
#define dbg(args...) do { cout << #args << " -> "; err(args); } while (0)
void err() { std::cout << std::endl; }
template<typename T, typename...Args>
void err(T a, Args...args) { std::cout << a << ' '; err(args...); }
template <template<typename...> class T, typename t, typename... A>
void err(const T <t> &arg, const A&... args) {
for (auto &v : arg) std::cout << v << ' '; err(args...); }
#else
#define dbg(...)
#endif
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
const int N = 1e5 + 5;

int n;
vector <int> G[N];
int in[N], out[N];
int least[N], most[N];
int sz[N];

void dfs0(int u, int fa) {
sz[u] = 1;
for (auto v : G[u]) if (v != fa) {
dfs0(v, u);
sz[u] += sz[v];
}
}

void dfs(int u, int fa) {
int all1 = 0, all2 = 0;
for (auto v : G[u]) if (v != fa) {
dfs(v, u);
all1 += least[v];
all2 += most[v];
}
least[u] = max(least[u], all1);
most[u] = min(most[u], all2 + (most[u] != 0));
}

bool check(int x) {
for (int i = 1; i <= n; i++) {
if (in[i] != -1) {
least[i] = in[i];
} else {
least[i] = 0;
}
if (out[i] != -1) {
most[i] = x - out[i];
} else {
most[i] = sz[i];
}
most[i] = min(most[i], sz[i]);
}
dfs(1, 0);
for (int i = 1; i <= n; i++) {
most[i] = min(most[i], sz[i]);
if (least[i] > most[i]) {
return false;
}
}
return least[1] <= x && x <= most[1];
}

void run() {
cin >> n;
for (int i = 1; i <= n; i++) {
G[i].clear();
in[i] = out[i] = -1;
}
for (int i = 1; i < n; i++) {
int u, v; cin >> u >> v;
G[u].push_back(v);
G[v].push_back(u);
}
dfs0(1, 0);
int A; cin >> A;
for (int i = 1; i <= A; i++) {
int x, y; cin >> x >> y;
in[x] = max(in[x], y);
}
int B; cin >> B;
for (int i = 1; i <= B; i++) {
int x, y; cin >> x >> y;
out[x] = max(out[x], y);
}
for (int i = 1; i <= n; i++) {
if (out[i] > n - sz[i] || in[i] > sz[i]) {
cout << -1 << '\n';
return;
}
}
int l = 0, r = n + 1, mid;
while (l < r) {
mid = (l + r) >> 1;
if (check(mid)) r = mid;
else l = mid + 1;
}
int ans = (r == n + 1 ? -1 : r);
cout << ans << '\n';
}

int main() {
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
cout << fixed << setprecision(20);
int T; cin >> T; while(T--)
run();
return 0;
}

posted @ 2020-06-20 20:27  heyuhhh  阅读(203)  评论(0编辑  收藏  举报