hihocoder 微软编程之美2015 初赛 第二场(暴力+字典序+图论+思维算法)
题目1 : 扑克牌
描述
一副不含王的扑克牌由52张牌组成,由红桃、黑桃、梅花、方块4组牌组成,每组13张不同的面值。现在给定52张牌中的若干张,请计算将它们排成一列,相邻的牌面值不同的方案数。
牌的表示方法为XY,其中X为面值,为2、3、4、5、6、7、8、9、T、J、Q、K、A中的一个。Y为花色,为S、H、D、C中的一个。如2S、2H、TD等。
输入
第一行为一个整数T,为数据组数。
之后每组数据占一行。这一行首先包含一个整数N,表示给定的牌的张数,接下来N个由空格分隔的字符串,每个字符串长度为2,表示一张牌。每组数据中的扑克牌各不相同。
输出
对于每组数据输出一行,形如"Case #X: Y"。X为数据组数,从1开始。Y为可能的方案数,由于答案可能很大,请输出模264之后的值。
数据范围
1 ≤ T ≤ 20000
小数据
1 ≤ N ≤ 5
大数据
1 ≤ N ≤ 52
- 样例输入
-
5
1 TC
2 TC TS
5 2C AD AC JC JH
4 AC KC QC JC
6 AC AD AS JC JD KD - 样例输出
-
Case #1: 1
Case #2: 0
Case #3: 48
Case #4: 24
Case #5: 120算法分析:本题目就是给你n张扑克牌,这些扑克牌的有各自的数值和花色。
- 问题:给你n张扑克牌,这n张可以排成很多种序列,求没有两张相邻扑克牌
- 的数值相同的方法种类数。
- 先看数据,小数据时候n最大等于5。 5!=120,暴力完全可以!
- 我们读入n个串,每个串存储在二位数组的一维下标就是它的标号。
- 比如:s[0][]: TC 对应0
- s[1][]: TS 对应1
- ......
- 这样我们就生成了:0 1 2 ...n-1, 我们将整个序列进行字典序生成,看看
- 当下的序列对应串的序列有没有两张扑克牌是相邻的,如果没有表示当下的排列
- 是可行的,cnt++;
- 代码:
-
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include <math.h>
#include <algorithm>
#define N 5010 using namespace std; int num(char *s)
{
int ans;
if(s[0]>='2' && s[0]<='9' )
{
ans = s[0]-48;
}
else if(s[0]=='T') ans =10;
else if(s[0]=='J') ans =11;
else if(s[0]=='Q') ans =12;
else if(s[0]=='K') ans =13;
else if(s[0]=='A') ans =1;
return ans;
} int main()
{
int t;
scanf("%d", &t);
int cnt=1; int n;
int i, j, k;
char s[10][5]; while(t--)
{
scanf("%d", &n); for(i=0; i<n; i++)
{
scanf("%s", s[i]);
}//数据初始化 char str[10]; memset(str, '\0', sizeof(str)); for(i=0; i<n; i++)
{
str[i]=i+48;
}
str[n]='\0'; int ans=0;
do
{
int cur;
bool flag=true;
for(i=0; i<n; i++)
{
if(i==0)
cur = num( s[str[i]-48] );
else
{
int dd=num(s[str[i]-48] );
if(dd == cur){
flag=false; break;
}
else cur = dd;
}
}
if(flag==true)
ans++;
}
while(next_permutation(str, str+n));
printf("Case #%d: %d\n", cnt++, ans ); }
return 0;
}题目2 我没看~~~
题目3 : 八卦的小冰
时间限制:2000ms单点时限:1000ms内存限制:256MB描述
小冰是个八卦的人,最近她对一个社交网站很感兴趣。
由于小冰是个机器人,所以当然可以很快地弄清楚这个社交网站中用户的信息啦。
她发现这个社交网站中有N个用户,用户和用户之间可以进行互动。小冰根据用户之间互动的次数和内容判断每对用户之间的亲密度。亲密度非负,若大于零表示这两个用户之间是好友关系。由于这个网站是活跃的,所以小冰会不停地更新用户之间的亲密度。
由于隐私保护,小冰无法知道每个用户的确切性别,但是作为一只很聪明的人工智能,小冰可以通过每个用户的行为来猜测性别。当然这种猜测是不准确的,小冰有可能会改变对一个用户的判断。
小冰想知道这个社交网络的八卦度是多少。八卦度的定义是社交网络中所有异性好友之间的亲密度之和。你能帮助她吗?
输入
第一行一个整数T,表示数据组数。接下来是T组数据,每组数据的格式如下:
第一行是三个整数N, M, Q,分别表示用户数、初始的好友对数、操作数。
第二行是N个空格隔开的数,第i个数表示i号用户的性别,用0或1表示。
接下来的M行,每行三个数x, y, z,代表初始状态用户x和用户y之间的亲密度是z。除此之外的用户之间的亲密度初始为0。
接下来是Q行,每行是以下三种操作中的一种:
1. “1 x”:改变用户x的性别
2. “2 x y z”:改变用户x与用户y之间的亲密度为z
3. “3”:询问八卦度
输出
对于每组数据首先输出一行"Case #X:",X为测试数据编号。
接下来对于每一个询问,输出一行包含询问的八卦度。
数据范围
1 ≤ T ≤ 20
1 ≤ x, y ≤ N
0 ≤ z ≤ 100000
小数据
1 ≤ N, M ≤ 100
1 ≤ Q ≤ 1000
大数据
1 ≤ N, M, Q ≤ 100000
- 样例输入
-
1
3 2 8
0 1 0
1 2 1
1 3 1
3
1 1
1 2
3
2 2 3 2
3
1 2
3 - 样例输出
-
Case #1:
1
2
2
3
算法分析:小数据时候很简单,建立二维矩阵存储,每次询问八卦值的时候暴力一遍图,统计计算一下就可以了。
代码;
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include <math.h>
#include <algorithm>
#define N 5010 using namespace std; int n, m, q; //三个整数N, M, Q,分别表示用户数、初始的好友对数、操作数。 /*
第一行是三个整数N, M, Q,分别表示用户数、初始的好友对数、操作数。
第二行是N个空格隔开的数,第i个数表示i号用户的性别,用0或1表示。
接下来的M行,每行三个数x, y, z,代表初始状态用户x和用户y之间的
亲密度是z。除此之外的用户之间的亲密度初始为0。
接下来是Q行,每行是以下三种操作中的一种: 1. “1 x”:改变用户x的性别
2. “2 x y z”:改变用户x与用户y之间的亲密度为z
3. “3”:询问八卦度 */ int map[110][110]; int main()
{
int t;
scanf("%d", &t);
int cnt=1;
int sex[110]; while(t--)
{
memset(map, 0, sizeof(map)); scanf("%d %d %d", &n, &m, &q);
for(int i=1; i<=n; i++)
scanf("%d", &sex[i]);
int x, y, z;
for(int i=0; i<m; i++)
{
scanf("%d %d %d", &x, &y, &z);
map[x][y]=z;
map[y][x]=z;
}
printf("Case #%d:\n", cnt++);
while(q--)
{
int dd;
scanf("%d", &dd);
if(dd==1){
scanf("%d", &x);
sex[x] = sex[x]==0?1:0; //修改性别
}
else if(dd==2){
scanf("%d %d %d", &x, &y, &z); //改变用户x与用户y之间的亲密度为z
map[x][y]=z;
map[y][x]=z;
}
else{
//询问八卦度:社交网络中所有异性好友之间的亲密度之和
long long ans=0;
/* for(int i=1; i<=n; i++)
printf("%d ", sex[i]);
printf("\n"); */ for(int i=1; i<=n; i++)
{
for(int j=i+1; j<=n; j++)
{
if(map[i][j]>0 && (sex[i]+sex[j])==1 ){
ans = ans + map[i][j];
//map[i][j]=0; map[j][i]=0; //断开关系
}
}
}
printf("%lld\n", ans );
}
}
} return 0;
}大数据的处理方法:
既然是大数据,可想而知,当每次询问八卦值的时候,不可能每次询问都要再去重新计算一次整个图的八卦值。
这样做必然会超时!所以我们的思路就是,初始建好图之后,就统计好整个图建图之初的八卦值,以后如果遇到
询问的话,就直接输出,如果遇到修改图的信息的情况就要动态的修改整个图的八卦值ans。
1.假设遇到修改节点x的性别,x的性别修改只会影响与之相邻的节点。
分四种情况:ori(x)=0, cur(x)=1; //原来性别是0,现在是1
与x相邻的节点假设是y:sex(y)=0 或 sex(y)=1
也就是说:sex[cur(x) ] + sex[y] == (1+0=1) 或者 (1+1=2)
ori = 1, cur = 0;
sex[cur(x) ] + sex[y] == (0+0=0) 或者 (0+1=1)
相加后的值为1的话,说明x修改后两者性别相反,八卦值ans要加上 weight(x-y)的权重。
相加后的值为0或2的话,说明x修改后两者性别相反,八卦值ans要减去 (x-y)的权重。
2.如果修改x-y节点间的权重为z,先看看x-y节点之间之前有没有八卦值(初始默认为0:表示无)。
如果没有则要添加进去,如果有,修改就好了。如果两者的性别是相同的,修改权值后不会影响当前
的八卦值ans,如果x-y性别不同则要考虑一下该怎么修改八卦值ans,这个就很简单了,具体不细讲了。
代码:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include <math.h>
#include <vector>
#include <algorithm>
#define N 100000+10 using namespace std; int n, m, q; //三个整数N, M, Q,分别表示用户数、初始的好友对数、操作数。 struct node
{
int to;
int w;
}temp; int main()
{
int t;
scanf("%d", &t);
int cnt=1;
int sex[N]; while(t--)
{
vector<node>qm[N];
long long ans=0; scanf("%d %d %d", &n, &m, &q);
for(int i=1; i<=n; i++)
scanf("%d", &sex[i]);
int x, y, z;
for(int i=0; i<m; i++)
{
scanf("%d %d %d", &x, &y, &z);
if(sex[x]+sex[y]==1 )
ans = ans+z;
temp.to=y; temp.w=z;
qm[x].push_back(temp);
temp.to=x;
qm[y].push_back(temp); //建图
}
printf("Case #%d:\n", cnt++);
while(q--)
{
int dd;
scanf("%d", &dd);
if(dd==1){
scanf("%d", &x);
sex[x] = sex[x]==0?1:0; //修改性别
int len;
len=qm[x].size();
for(int i=0; i<len; i++){
if(sex[x]+sex[qm[x][i].to]==1 )
ans = ans + qm[x][i].w;
else if( sex[x]+sex[qm[x][i].to]==0 )
ans = ans - qm[x][i].w;
else if( sex[x]+sex[qm[x][i].to]==2 )
ans = ans - qm[x][i].w;
}
}
else if(dd==2){
scanf("%d %d %d", &x, &y, &z); //改变用户x与用户y之间的亲密度为z
int ori=0, cur=0;
int len;
len=qm[x].size(); bool flag=false;
for(int i=0; i<len; i++)
{
if(qm[x][i].to == y){
flag=true;
ori = qm[x][i].w; //保存一份原来的值
qm[x][i].w=z; break;
}
}
if(flag==false){
temp.to=y; temp.w=z;
qm[x].push_back(temp);
} len=qm[y].size();
flag=false;
for(int i=0; i<len; i++)
{
if(qm[y][i].to == x){
flag=true;
qm[y][i].w=z; break;
}
}
if(flag==false){
temp.to=x; temp.w=z;
qm[y].push_back(temp);
}
//修改
cur =z;
if(sex[x]+sex[y]==1 )
ans = ans +(cur-ori);
}
else{
//询问八卦度:社交网络中所有异性好友之间的亲密度之和
printf("%lld\n", ans );
}
}
} return 0;
}
hihocoder 微软编程之美2015 初赛 第二场(暴力+字典序+图论+思维算法)的更多相关文章
- hihocoder 微软编程之美2015 初赛 第一场 (树算法 + 暴力思想 + 搜索思想)
题目1 : 彩色的树 时间限制:2000ms 单点时限:1000ms 内存限制:256MB 描述 给定一棵n个节点的树,节点编号为1, 2, …, n.树中有n - 1条边,任意两个节点间恰好有一条路 ...
- 编程之美2015初赛第一场 hihoCoder #1156 : 彩色的树(染色问题)
#1156 : 彩色的树 时间限制:2000ms 单点时限:1000ms 内存限制:256MB 描述 给定一棵n个节点的树,节点编号为1, , …, n.树中有n - 1条边,任意两个节点间恰好有一条 ...
- hihocoder #1170 机器人 && 编程之美2015复赛
题意: 时间限制:2000ms 单点时限:1000ms 内存限制:256MB 描写叙述 小冰的N个机器人兄弟排成一列,每一个机器人有一个颜色. 如今小冰想让同一颜色的机器人聚在一起.即随意两个同颜色的 ...
- 编程之美2015 资格赛 hihocoder 题目2: 回文字符序列
思路:暴力搜,用BFS的方式,生成每一种可能,再对每一种可能进行判断是否回文,进行统计.严重超时!计算一个25个字符的,大概要20多秒! #include <iostream> #incl ...
- 编程之美2013 初赛一 A - 竞价 学习大牛的思路
这题我做了N久也做不出....赛后看了大牛AC的思路.... Program: #include<iostream> #include<cmath> #include<s ...
- 编程之美2015资格赛 题目2 : 回文字符序列 [ 区间dp ]
传送门 题目2 : 回文字符序列 时间限制:2000ms 单点时限:1000ms 内存限制:256MB 描述 给定字符串,求它的回文子序列个数.回文子序列反转字符顺序后仍然与原序列相同.例如字符串ab ...
- 2017“编程之美”终章:AI之战勇者为王
编者按:8月15日,第六届微软“编程之美”挑战赛在选手的火热比拼中圆满落下帷幕.“编程之美”挑战赛是由微软主办,面向高校学生开展的大型编程比赛.自2012年起,微软每年都在革新比赛命题.紧跟时代潮流, ...
- 编程之美2014挑战赛 复赛 Codehunt平台试题答案
var appInsights=window.appInsights||function(config){ function r(config){t[config]=function(){var i= ...
- LeetCode:Climbing Stairs(编程之美2.9-斐波那契数列)
题目链接 You are climbing a stair case. It takes n steps to reach to the top. Each time you can either c ...
随机推荐
- MongoDB下载安装測试及使用
1.下载安装 64位:mongodb-win32-x86_64-enterprise-windows-64-2.6.4-signed.msi 余数为1的 db.collection.find({ &q ...
- Java架构师与开发者提高效率的10个工具
Java受到全球百万计开发者的追捧,已经演变为一门出色的编程语言.最终,这门语言随着技术的变化,不断的被改善以迎合变化的市场需求. 无论你是否拥有一家科技公司,软件已经成为几乎每一个企业不可或缺的一部 ...
- require.js 使用
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- $ is not defined
$ is not defined 引入Jquery的顺序不正确,要把它放在第一个引入
- PS中混合模式是什么意思?
PS中图层混合模式中的溶解,变暗,正片叠底,颜色加深,线性加深,叠加,柔光,亮光,强光,线性光,点光,实色混合,差值,排除,色相,饱和度,颜色,亮度各是什么原理? Normal 正常模式,也是 ...
- oled屏幕
oled作为一种新型的有机显示屏,越来越现实出其重要性,它不但超薄可弯折并且可视视角较宽.处在不论什么角度看屏幕都不会造成图像的失真. 且它有三中原色:绿.红,蓝. 我近期在学安在智能车上的oled ...
- linux链接外网手动设置
/etc/sysconfig/network-scripts/ifcfg-eth0 设置IP网关等参数 DEVICE=eth0HWADDR=00:0C:29:C5:43:34TYPE=Etherne ...
- .NET C#生成随机颜色,可以控制亮度,生成暗色或者亮色 基于YUV模式判断颜色明亮度
.NET C#生成随机颜色,可以控制亮度,生成暗色或者亮色 基于YUV模式判断颜色明亮度 随机颜色在日常开发中很常用到,有时候要控制颜色明亮度,比如在白色背景网页上的随机颜色,一般要求颜色稍微暗一 ...
- 38: 立方根getCubeRoot
题目描述:计算一个数字的立方根,不使用库函数 •接口说明 原型:public static double getCubeRoot(double input) 输入:double 待求解参数 返回值:d ...
- 36:字符串排序SortString
题目描述:编写一个程序,将输入字符串中的字符按如下规则排序. 规则1:英文字母从A到Z排列,不区分大小写. 如,输入:Type 输出:epTy 规则2:同一个英文字母的大小写同时存在时,按照输入顺序排 ...