2015长春网赛

1001题就是直接模拟就好,但是有坑点,就是后面给的开门的时间点需要排下序,wa到比赛快结束了菜反应过来,可能也是第一次做这种比赛有点紧张吧;委屈

#include "iostream"
#include "cstdio"
#include "cstdlib"
#include "cstring"
#include "climits"
#include "queue"
#include "cmath"
#include "map"
#include "set"
#include "stack"
#include "vector"
#include "sstream"
#include "algorithm"
using namespace std;
const int inf=1e8;
const int maxn=150000+100;
typedef long long ll;
typedef unsigned long long ull;
struct person
{
    char name[300];
    int v,id;
    bool operator < (const person & rhs) const
    {
        if(v!=rhs.v)
            return v<rhs.v;
        else 
            return id>rhs.id;
    }
};
person a[maxn];
int k,m,q,t,p;
int ans[maxn];
int que[maxn];
struct data
{
    int t,p;
}mm[maxn];
bool cmp(data left,data right)
{
    return left.t<right.t;
}
int main()
{    
    //ios::sync_with_stdio(false);
    // freopen("in.txt","r",stdin);
    //freopen("out.txt","w",stdout);
    int T;
    scanf("%d",&T);
    priority_queue<person>     pq;
    while(T--)
    {
        while(!pq.empty())
            pq.pop();
        scanf("%d%d%d",&k,&m,&q);
        for(int i=1;i<=k;i++)
        {
            scanf("%s%d",a[i].name,&a[i].v);
            a[i].id=i;
        }
        int last=1;
        int cnt=0;
        for(int i=1;i<=m;i++)
            scanf("%d%d",&mm[i].t,&mm[i].p);
        sort(mm+1,mm+m+1,cmp);
        for(int i=1;i<=m;i++)
        {
           
            for(int j=last;j<=mm[i].t;j++)
                pq.push(a[j]);
            last=mm[i].t+1;
            for(int j=1;j<=mm[i].p&&!pq.empty();j++)
            {
                person tmp=pq.top();
                ans[++cnt]=tmp.id;
                pq.pop();
            }    
        }
        if(last<=k)
        {
            for(int j=last;j<=k;j++)
                pq.push(a[j]);
        }
        int maxv=0;
        for(int i=1;i<=q;i++)
        {
            scanf("%d",&que[i]);
            maxv=max(maxv,que[i]);
        }
        for(cnt++;cnt<=maxv;cnt++)
        {
            person tmp=pq.top();
            ans[cnt]=tmp.id;
            pq.pop();
        }
        for(int i=1;i<=q;i++)
        {
            printf("%s",a[ans[que[i]]].name);
            if(i!=q)
                printf(" ");
        }
        printf("\n");
    }
    return 0;
}

1002题要先根据条件删除一下点,也就是度为一的点,同时与之相连的点的度数也要减1,知道再也找不到度为一的点了;然后就是用并查集了,记录每个连通块中点的数目以及该连通块中点权的和,注意要用long long,不然怎么死的都不知道;因为long long 的原因知道快结束了才搞定,日了dog了。。。。

/*****************************************
Author      :Crazy_AC(JamesQi)
Time        :2015
File Name   :
*****************************************/
// #pragma comment(linker, "/STACK:1024000000,1024000000")
#include <iostream>
#include <algorithm>
#include <iomanip>
#include <sstream>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <vector>
#include <map>
#include <set>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <limits.h>
using namespace std;
#define MEM(a,b) memset(a,b,sizeof a)
#define pk push_back
template<class T> inline T Get_Max(const T&a,const T&b){return a < b?b:a;}
template<class T> inline T Get_Min(const T&a,const T&b){return a < b?a:b;}
typedef long long ll;
typedef pair<int,int> ii;
const int inf = 1 << 30;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const int maxn = 1e5 + 10;
ii E[maxn];
int val[maxn];
int F[maxn];
int in[maxn];

int cnt[maxn];
ll sum[maxn];

int n,m;
int Find(int x){
	if (F[x] == x) return x;
	else return F[x] = Find(F[x]);
}
int main()
{	
	// ios::sync_with_stdio(false);
	// freopen("in.txt","r",stdin);
	// freopen("out.txt","w",stdout);
	int T;
	scanf("%d",&T);
	while(T--){
		scanf("%d%d",&n,&m);
		for (int i = 1;i <= n;++i){
			scanf("%lld",&sum[i]);
			F[i] = i;
			cnt[i] = 1;
		}
		MEM(in, 0);
		for (int i = 1;i <= m;++i){
			scanf("%d%d",&E[i].first,&E[i].second);
			in[E[i].first]++;
			in[E[i].second]++;
		}
		bool flag = true;
		while(flag){
			flag = false;
			for (int i = 1;i <= m;++i){
				if (in[E[i].first] == 0 || in[E[i].second] == 0) continue;
				if ((in[E[i].first] != 0 && in[E[i].second] != 0) && (in[E[i].first] < 2 || in[E[i].second] < 2)){
					in[E[i].first]--;
					in[E[i].second]--;
					flag = true;
				}
				else continue;
			}
		}
		// MEM(sum ,0);
		// MEM(cnt, 0);
		for (int i = 1;i <= m;++i){
			if (in[E[i].first] && in[E[i].second]){
				int t1 = Find(E[i].first);
				int t2 = Find(E[i].second);
				if (t1 != t2){
					F[t1] = t2;
					cnt[t2] += cnt[t1];
					sum[t2] += sum[t1];
				}
			}
		}
		ll ans = 0;
		for (int i = 1;i <= n;++i){
			if (!in[i]) continue;
			if (F[i] == i && cnt[i] > 1 && cnt[i] & 1)
				ans += sum[i];
		}
		printf("%lld\n",ans);
	}
	return 0;
}
1005题也是一个并查集的简单应用,因为某种不想吐槽的原因导致比赛的时候没做出来,原因就不说了;

这里注意人可以在每个点休息,但是不能在路上待的时间超过limit,用了一点贪心点思想,如果limit1 < limit2,

那么使用与limit1的情况也适用于limit2的情况;所以对所有的limit进行排序,再使用并查集求连通块中点的数目,

由于是求点对<u,v> 与 <v,u>是不同的;最后对于该limit的点对总和就应该是sum(cnt[i] * (cnt[i]  - 1));

最后对应输出就好了;

/*****************************************
Author      :Crazy_AC(JamesQi)
Time        :2015
File Name   :
*****************************************/
// #pragma comment(linker, "/STACK:1024000000,1024000000")
#include <iostream>
#include <algorithm>
#include <iomanip>
#include <sstream>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <vector>
#include <map>
#include <set>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <limits.h>
using namespace std;
#define MEM(a,b) memset(a,b,sizeof a)
#define pk push_back
template<class T> inline T Get_Max(const T&a,const T&b){return a < b?b:a;}
template<class T> inline T Get_Min(const T&a,const T&b){return a < b?a:b;}
typedef long long ll;
typedef pair<int,int> ii;
const int inf = 1 << 30;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const int N = 2e4 + 10;
const int M = 1e5 + 10;
int F[N];
int cnt[N];
int n,m,q;
struct Edge{
	int u,v,w;
	bool operator < (const Edge& b)const{
		return w < b.w;
	}
}E[M];
int Find(int x){
	if (F[x] == x) return x;
	else return F[x] = Find(F[x]);
}
int main()
{	
	// ios::sync_with_stdio(false);
	// freopen("in.txt","r",stdin);
	// freopen("out.txt","w",stdout);
	int T;
	scanf("%d",&T);
	while(T--){
		scanf("%d%d%d",&n,&m,&q);
		for (int i = 1;i <= n;++i) {
			F[i] = i;
			cnt[i] = 1;
		}
		for (int i = 1;i <= m;++i){
			scanf("%d%d%d",&E[i].u,&E[i].v,&E[i].w);
		}
		sort(E + 1,E + m + 1);
		ii rec[N];
		for (int i = 1;i <= q;++i){
			scanf("%d",&rec[i].first);
			rec[i].second = i;
		}
		sort(rec + 1,rec + 1 + q);
		int out[N];
		int last = 1;
		for (int i = 1;i <= q;++i){
			int limit = rec[i].first;
			// int cnt = 1;
			int j;
			for (j = last;j <= m;++j){
				if (E[j].w > limit) break;
				int t1 = Find(E[j].u);
				int t2 = Find(E[j].v);
				if (t1 != t2){
					F[t1] = t2;
					cnt[t2] += cnt[t1];
				}
			}
			last = j;
			ll tmp = 0;
			for (j = 1;j <= n;++j){
				if (F[j] == j && cnt[j] > 1)
					tmp += cnt[j] * (cnt[j] - 1) ;
			}
			out[rec[i].second] = tmp;
		}
		for (int i = 1;i <= q;++i)
			printf("%d\n",out[i]);
	}
	return 0;
}

1006题就是字符串的最大表示法模板题;

#include <iostream>
#include <cstdio>
#include <complex>
#include <algorithm>
#include <cmath>
#include <cstring>
#include <vector>
#include <set>
#include <map>
#include <queue>
#include <cctype>
typedef unsigned long long ull ;
typedef long long ll ;
using namespace std ;
const double eps = 1e-10 , pi = acos(-1.0) ;
const int maxn = 20000 + 5 ;
const int maxm = 200000 + 5 ;
const int inf = 0x3f3f3f3f ;
const ll mod = 1e9 + 7 ;
const ull C = 123 ;

char s[maxn] , ss[maxn*2] ;
int n , T ;
ull Hash[maxn*2] , P ;


int maxPresent( char *s , int n )
{
    int i = 0 , j = 1 , k = 0 , t ;
    while( i < n && j < n && k < n )
    {
        t = s[(i+k)%n] - s[(j+k)%n] ;
        if( !t ) k++ ;
        else
        {
            if( t < 0 ) i += k+1 ;
            else j += k+1 ;
            if( i == j ) j++ ;
            k = 0 ;
        }
    }
    return min(i,j) ;
}

void getHash( char *s , int n )
{
    Hash[n] = 0 ;
    for( int i = n-1 ; i >= 0 ; i-- )
    {
        Hash[i] = Hash[i+1] * C + s[i] ;
    }
}

ull getCode( int pos , int n )
{
    return Hash[pos] - Hash[pos+n] * P ;
}

int maxIndex( char *s , int n , int k )
{
    getHash(s,n*2) ; P = 1 ;
    for( int i = 0 ; i < n ; i++ ) P *= C ;
    ull code = getCode(k,n) ;
    for( int i = n-1 ; i > k ; i-- )
    {
        if( getCode(i,n) == code ) return i ;
    }
    return k ;
}

int main()
{
    scanf( "%d" , &T ) ;
    while( T-- )
    {
        scanf( "%d%s" , &n , s ) ;
        for( int i = 0 ; i < n ; i++ ) ss[i] = ss[i+n] = s[n-i-1] ;
        int a = maxPresent(s,n) , b = maxPresent(ss,n) ;
        b = maxIndex(ss,n,b) ;
        int k = 0 , f = 0 ;
        for( int i = a , j = b ; k < n ; k++ , i = (i+1)%n , j = (j+1)%n )
        {
            if( s[i] == ss[j] ) continue ;
            else
            {
                if( s[i] < ss[j] ) f = 1 ;
                break ;
            }
        }
        a = a+1 ;
        b = n-b ;
        if( k == n )
        {
            if( a > b ) printf( "%d %d\n" , b , 1 ) ;
            else printf( "%d %d\n" , a , 0 ) ;
        }
        else
        {
            if( f == 1 ) printf( "%d %d\n" , b , 1 ) ;
            else printf( "%d %d\n" , a , 0 ) ;
        }
    }
    return 0 ;
}

1008就是裸的二叉树重建,然后dfs输出路径;这种题一定要注意界限的问题RE了7发ORZ。。。

/*****************************************
Author      :Crazy_AC(JamesQi)
Time        :2015
File Name   :
*****************************************/
// #pragma comment(linker, "/STACK:1024000000,1024000000")
#include <iostream>
#include <algorithm>
#include <iomanip>
#include <sstream>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <vector>
#include <map>
#include <set>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <limits.h>
using namespace std;
#define MEM(a,b) memset(a,b,sizeof a)
#define pk push_back
template<class T> inline T Get_Max(const T&a,const T&b){return a < b?b:a;}
template<class T> inline T Get_Min(const T&a,const T&b){return a < b?a:b;}
typedef long long ll;
typedef pair<int,int> ii;
const int inf = 1 << 30;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const int maxn = 1e5 + 10;
int n,q;
int ls[maxn];
int rs[maxn];
int val[maxn];
int top;
int new_node(int x){
	++top;
	ls[top] = rs[top] = 0;
	val[top] = x;
	return top;
}
int insert(int rt,int num){
	if (!val[rt]) return new_node(num);
	if (num < val[rt]) ls[rt] = insert(ls[rt],num);
	else rs[rt] = insert(rs[rt],num);
	return rt;
}
void Query(int rt,int num){
	if (num < val[rt]) {
		putchar('E');
		Query(ls[rt],num);
	}
	else if (num > val[rt]){
		putchar('W');
		Query(rs[rt],num);
	}
}
int main()
{	
	// ios::sync_with_stdio(false);
	// freopen("in.txt","r",stdin);
	// freopen("out.txt","w",stdout);
	int T;
	scanf("%d",&T);
	while(T--){
		scanf("%d",&n);
		int x;
		MEM(val, 0);
		top = 0;
		for (int i = 1;i <= n;++i){
			scanf("%d",&x);
			insert(1,x);
		}
		scanf("%d",&q);
		while(q--){
			scanf("%d",&x);
			Query(1,x);
			printf("\n");
		}
	}
	return 0;
}

1007题就是裸的RMQ,用线段树和ST都是可以的;

/*****************************************
Author      :Crazy_AC(JamesQi)
Time        :2015
File Name   :
*****************************************/
// #pragma comment(linker, "/STACK:1024000000,1024000000")
#include <iostream>
#include <algorithm>
#include <iomanip>
#include <sstream>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <vector>
#include <map>
#include <set>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <limits.h>
using namespace std;
#define MEM(a,b) memset(a,b,sizeof a)
#define pk push_back
template<class T> inline T Get_Max(const T&a,const T&b){return a < b?b:a;}
template<class T> inline T Get_Min(const T&a,const T&b){return a < b?a:b;}
typedef long long ll;
typedef pair<int,int> ii;
const int inf = 1 << 30;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const int maxn = 1010;
int T,n,Q;
int MAX[maxn * 3];
void Built(int rt,int l,int r){
	if (l == r){
		scanf("%d",&MAX[rt]);
		return ;
	}
	int mid = (l + r) >> 1;
	Built(rt << 1,l,mid);
	Built(rt << 1 | 1,mid + 1,r);
	MAX[rt] = Get_Max(MAX[rt << 1],MAX[rt << 1 | 1]);
}

int Query(int rt,int L,int R,int l,int r){
	if (l <= L && R <= r) return MAX[rt];
	int mid = (L + R) >> 1;
	int ret = 0;
	if (l <= mid) ret = Get_Max(ret,Query(rt << 1,L,mid,l,r));
	if (r > mid) ret = Get_Max(ret,Query(rt << 1 | 1,mid + 1,R,l,r));
	return ret;
}

int main()
{	
	// ios::sync_with_stdio(false);
	// freopen("in.txt","r",stdin);
	// freopen("out.txt","w",stdout);
	scanf("%d",&T);
	while(T--){
		MEM(MAX, 0);
		scanf("%d",&n);
		Built(1,1,n);
		int a,b;
		scanf("%d",&Q);
		while(Q--){
			scanf("%d%d",&a,&b);
			printf("%d\n",Query(1,1,n,a,b));
		}
	}
	return 0;
}

1010Lcase + CRT模板题,只是要注意中间结果爆long long,所以此时我们就用了快速幂边乘边取摸,最后返回值也要先取摸;

/*****************************************
Author      :Crazy_AC(JamesQi)
Time        :2015
File Name   :
*****************************************/
// #pragma comment(linker, "/STACK:1024000000,1024000000")
#include <iostream>
#include <algorithm>
#include <iomanip>
#include <sstream>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <vector>
#include <map>
#include <set>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <limits.h>
using namespace std;
#define MEM(a,b) memset(a,b,sizeof a)
#define pk push_back
template<class T> inline T Get_Max(const T&a,const T&b){return a < b?b:a;}
template<class T> inline T Get_Min(const T&a,const T&b){return a < b?a:b;}
typedef long long ll;
typedef pair<int,int> ii;
const int inf = 1 << 30;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const int N = 1e5 + 10;
const int M = 1e5 + 10;
ll n,m,k;
ll a[12],mm[12];
ll Quick_Mod(ll x,ll y,ll p){
	ll rec = 1;
	x %= p;
	while(y){
		if (y & 1) rec = rec * x % p;
		y >>= 1;
		x = x * x % p;
	}
	return rec;
}

ll C(ll n,ll m,ll p){
	if (m > n) return 0;
	ll ans = 1;
	for (int i = 1;i <= m;++i){
		ll a = (n + i - m) % p;
		ll b = i % p;
		ans = ans * (a * Quick_Mod(b,p - 2,p) % p) % p;
	}
	return ans;
}

ll Lucas(ll n,ll m, ll p){
	if (m == 0) return 1;
	return C(n % p,m % p , p) * Lucas(n / p,m / p,p) % p;
}

ll Extend_Euclid(ll a,ll b,ll& x,ll& y){
	ll d;
	if (b == 0){
		x = 1;
		y = 0;
		return a;
	}
	d = Extend_Euclid(b, a % b,y,x);
	y -= a / b * x;
	return d;
}

ll mod_mul(ll a,ll b,ll mod){
	ll ret = 0;
	while(b){
		if (b & 1) ret = (ret + a) % mod;
		a = (a + a) % mod;
		b >>= 1;
	}
	return ret;
}

ll CRT(){
	ll d,x,y,tmp,M,ret;
	ret = 0;
	M = 1;
	for (int i = 0;i < k;i++)
		M *= mm[i];
	for (int i = 0;i < k;++i){
		tmp = M / mm[i];
		d = Extend_Euclid(mm[i],tmp,x,y);
		ll temp = mod_mul(y,tmp,M);
		temp = mod_mul(temp,a[i],M);
		ret = (ret + temp) % M;
	}
	return (M + ret) % M;
}



int main()
{	
	// ios::sync_with_stdio(false);
	// freopen("in.txt","r",stdin);
	// freopen("out.txt","w",stdout);
	int T;
	cin >> T;
	while(T--){
		cin >> n >> m >> k;
		for (int i = 0;i < k;++i){
			cin >> mm[i];
			a[i] = Lucas(n,m,mm[i]);
		}
		cout << CRT() << endl;
	}
	return 0;
}

总结:虽然才学习一年,很多知识点掌握得都不够,原因有多总,来自学校和学长还有队里面的就不说了;

主要还是自己跟着不良风气走歪了,没能按照自己预定的计划进行训练,可能也是上大学后自己,

一个人,没有人管着,所以时间安排也是一团糟糕;但愿后面能静心做自己的事,不在受他人影响,

从来都是坚信,努力就会成功;做自己的也才是最对得起自己;

ps:这场网赛糟糕透了,,,后面继续努力,调整状态;

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值