BestCoder Round #47 ($)
2015-07-11 21:22
337 查看
1001:Senior's Array
题目大意:
在数组中改一个合适的数(必须修改)使得区间和最大的那个区间的和尽量大,问最大区间和是多大?
解题思路:
数据范围比较小,水题,可以暴力,枚举修改的数字,然后求区间和最大的,最后比较得出最大。
1002:Senior's Gun
题目大意:
有n个技能,m个怪兽,当技能的伤害力x大于怪兽的防卫能力y,这个技能就可以消灭这个怪兽,并且得到x-y的分数,怪兽可以不被消灭完,问最大得分是多少?
解题思路:
简单贪心,把技能值和怪兽能力值排序,用最大的技能值减去最小的怪兽防御能力,直到最后没有技能可以消灭怪兽。
1003:Senior's String
题目连接:
http://acm.hdu.edu.cn/showproblem.php?pid=5282
题目描述:
给出两个字符串x,y。假设L为两个字符串的最长公共子序列,问把x拆成若干个长度为L的子序列中有几个是y的子序列?
解题思路:
首先用O(n^2)的方法求出x,y的最长公共子序列数组dp[i][j],然后再用一个数组dp1[i][j]来表示x前i个字符与y的前j个字符最长公共子序列等于dp[i][j]的方案数,对于dp1[i][j]的计算也是对dp[i][j]数组转移策略的讨论。只需要考虑选还是不选x的第i个字符即可。
题目大意:
在数组中改一个合适的数(必须修改)使得区间和最大的那个区间的和尽量大,问最大区间和是多大?
解题思路:
数据范围比较小,水题,可以暴力,枚举修改的数字,然后求区间和最大的,最后比较得出最大。
#include <cstdio> #include <cstring> #include <iostream> #include <algorithm> using namespace std; const int maxn = 1010; const int INF = 0x3f3f3f3f; typedef __int64 LL; int main () { LL t, a[maxn]; scanf ("%I64d", &t); while (t --) { LL n, m; scanf ("%I64d %I64d", &n, &m); for (int i=0; i<n; i++) scanf ("%I64d", &a[i]); LL Max = -INF; for (int i=0; i<n; i++) { swap (m, a[i]); LL sum, num; sum = num = -INF; for (int j=0; j<n; j++) { if (num < 0) num = a[j]; else num += a[j]; if (num > sum) sum = num; } if (sum > Max) Max = sum; swap (m, a[i]); } printf ("%I64d\n", Max); } return 0; }
1002:Senior's Gun
题目大意:
有n个技能,m个怪兽,当技能的伤害力x大于怪兽的防卫能力y,这个技能就可以消灭这个怪兽,并且得到x-y的分数,怪兽可以不被消灭完,问最大得分是多少?
解题思路:
简单贪心,把技能值和怪兽能力值排序,用最大的技能值减去最小的怪兽防御能力,直到最后没有技能可以消灭怪兽。
#include <cstdio> #include <cstring> #include <iostream> #include <algorithm> using namespace std; const int maxn = 100010; const int INF = 0x3f3f3f3f; typedef __int64 LL; LL a[maxn], b[maxn]; int main () { int t; scanf ("%d", &t); while (t --) { int n, m; scanf ("%d %d", &n, &m); for (int i=0; i<n; i++) scanf ("%I64d", &a[i]); for (int i=0; i<m; i++) scanf ("%I64d", &b[i]); sort (a, a+n); sort (b, b+m); LL sum = 0; for (int i=n-1,j=0;i>=0&&j<m; i--,j++) { if (a[i] < b[j]) break; sum += a[i] - b[j];; } printf ("%I64d\n", sum); } return 0; }
1003:Senior's String
题目连接:
http://acm.hdu.edu.cn/showproblem.php?pid=5282
题目描述:
给出两个字符串x,y。假设L为两个字符串的最长公共子序列,问把x拆成若干个长度为L的子序列中有几个是y的子序列?
解题思路:
首先用O(n^2)的方法求出x,y的最长公共子序列数组dp[i][j],然后再用一个数组dp1[i][j]来表示x前i个字符与y的前j个字符最长公共子序列等于dp[i][j]的方案数,对于dp1[i][j]的计算也是对dp[i][j]数组转移策略的讨论。只需要考虑选还是不选x的第i个字符即可。
#include <cstdio> #include <cstring> #include <iostream> #include <algorithm> using namespace std; const int maxn = 1010; const int mod = 1000000007; int dp[maxn][maxn], dp1[maxn][maxn], a[maxn][30]; char x[maxn], y[maxn]; int main () { int t; scanf ("%d", &t); while (t --) { scanf ("%s %s", x, y); int nx = strlen (x); int ny = strlen (y); int temp[30]; memset (a, 0, sizeof(a)); memset (dp, 0, sizeof(dp)); memset (dp1, 0, sizeof(dp1)); memset (temp, 0, sizeof(temp)); for (int i=1; i<=ny; i++) { temp[y[i-1]-'a'] = i; for (int j=0; j<26; j++) a[i][j] = temp[j]; } for (int i=1; i<=nx; i++) for (int j=1; j<=ny; j++) if (x[i-1] == y[j-1]) dp[i][j] = dp[i-1][j-1] + 1; else dp[i][j] = max(dp[i][j-1], dp[i-1][j]); for (int i=0; i<=nx; i++) for (int j=0; j<=ny; j++) { if (dp[i][j] == 0) { dp1[i][j] = 1; continue; } if (dp[i][j] == dp[i-1][j]) dp1[i][j] = (dp1[i][j] + dp1[i-1][j]) % mod; int p = a[j][x[i-1]-'a']; if (p && dp[i-1][p-1] + 1 == dp[i][j]) dp1[i][j] = (dp1[i][j] + dp1[i-1][p-1]) % mod; } printf ("%d\n", dp1[nx][ny]); } return 0; }
相关文章推荐
- 201507月推荐书籍
- 1021. 个位数统计 (15)
- [LeetCode] Max Points on a Line
- php相关
- 我为什么要写博客?
- 转换到 COFF 期间失败: 文件无效或损坏
- 我本来想发张照片来着
- 1020. 月饼 (25)
- 逗比问题,特此留念
- Hibernate映射集合属性的两种方式(非关联映射)--基础
- 关于Java面向对象的初体验
- 【学习笔记】【OC语言】面向对象思想
- leetcode刷题,总结,记录 ,备忘48
- 关于struts2中关于值栈的总结
- (转载)Peter Norvig:十年学会编程
- Java - Thinking in Java 第5章 习题
- 异常
- 1019. 数字黑洞 (20)
- C#中如何將文件地址存入数据库
- 【JAVA学习】(二)JAVA 多线程同步