BestCoder Round #85 (hdu5776,hdu5777,hdu5776)
来源:互联网 发布:君子去仁 恶乎成名 编辑:程序博客网 时间:2024/05/22 14:51
sum
题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=5776
解题思路:
中文题目:
问题描述
给定一个数列,求是否存在连续子列和为m的倍数,存在输出YES,否则输出NO
输入描述
输入文件的第一行有一个正整数T(1≤T≤10),表示数据组数。接下去有T组数据,每组数据的第一行有两个正整数n,m (1≤n≤100000 ,1≤m≤5000).第二行有n个正整数x (1≤x≤100)表示这个数列。
输出描述
输出T行,每行一个YES或NO。
输入样例
23 31 2 35 76 6 6 6 6
输出样例
YESNO
预处理前缀和,一旦有两个数模m的值相同,说明中间一部分连续子列可以组成m的倍数。 另外,利用抽屉原理,我们可以得到,一旦n大于等于m,答案一定是YES 复杂度 O(n)
AC代码:
#include <iostream>#include <cstdio>#include <cstring>using namespace std;const int N = 100005;const int M = 5005;int sum[N],cnt[M];int main(){ int T; scanf("%d",&T); while (T--){ int n,m; scanf("%d%d",&n,&m); memset(cnt,0,sizeof(cnt)); cnt[0] = 1; for(int i = 1; i <= n; ++i){ int x; scanf("%d",&x); sum[i] = (sum[i-1]+x)%m; ++cnt[sum[i]]; } bool flag = 0; for(int i = 0; i < m; ++i){ if(cnt[i] > 1){ flag = 1; break; } } puts(flag?"YES":"NO"); } return 0;}
domino
题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=5777
解题思路:
中文题目:
问题描述
小白在玩一个游戏。桌子上有n张多米诺骨牌排成一列。它有k次机会,每次可以选一个还没有倒的骨牌,向左或者向右推倒。每个骨牌倒下的时候,若碰到了未倒下的骨牌,可以把它推倒。小白现在可以随意设置骨牌的高度,但是骨牌高度为整数,且至少为1,并且小白希望在能够推倒所有骨牌的前提下,使所有骨牌高度的和最小。
输入描述
第一行输入一个整数T(1≤T≤10)每组数据有两行第一行有两个整数n和k,分别表示骨牌张数和机会次数。(2≤k,n≤100000)第二行有n-1个整数,分别表示相邻骨牌的距离d,1≤d≤100000
输出描述
对于每组数据,输出一行,最小的高度和
输入样例
14 22 3 4
输出样例
9算法思想:
首先骨牌只要考虑都往右推,其次能带倒骨牌的前提是高度大于等于距离+1。所以如果推一次,那么就是骨牌高度=离下一块骨牌距离+1. 把第一块左边距离设为无穷大,能推nk次,那么就是找nk块左边距离最大的向右推倒即可,所以只需要排序找到前nk-1大的距离。 有个小trick,推的次数可能大于骨牌数量 复杂度 O(nlogn)
AC代码:
#include <iostream>#include <cstdio>#include <cstring>#include <algorithm>using namespace std;typedef long long ll;const int N = 100005;int d[N];int main(){ int T; scanf("%d",&T); while (T--){ int n,k; scanf("%d%d",&n,&k); ll ans = min(n,k); for(int i = 1; i < n; ++i) scanf("%d",&d[i]); sort(d+1,d+n); for(int i = 1; i+k-1 < n; ++i) ans += d[i]+1; printf("%lld\n",ans); } return 0;}
abs
题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=5778
解题思路:
中文题目:
问题描述
给定一个数x,求正整数y≥2,使得满足以下条件:1.y-x的绝对值最小2.y的质因数分解式中每个质因数均恰好出现2次。
输入描述
第一行输入一个整数T(1≤T≤50)每组数据有一行,一个整数x(1≤x≤1018)
输出描述
对于每组数据,输出一行y-x的最小绝对值
输入样例
511124290871699579095
输出样例
23656724470算法思想:
由于y质因数分解式中每个质因数均出现2次,那么y是一个完全平方数,设y=z*z,题目可转换成求z,使得每个质因数出现1次. 我们可以暴力枚举z,检查z是否符合要求,显然当z是质数是符合要求,由素数定理可以得,z的枚举量在logn级别 复杂度 O(4√nlog2√n)
AC代码:
#include <iostream>#include <cstdio>#include <cstring>#include <vector>#include <cmath>#include <algorithm>using namespace std;typedef long long ll;const int N = 100005;const ll INF = 0x3f3f3f3f;vector<int> prime;int vis[N],num_prime = 0;void get_prime(){ memset(vis,0,sizeof(vis)); prime.clear(); for(int i = 2; i < N; i++){ int tt = N/i; for(int j = 2; j <= tt; j++) vis[i*j] = 1; } for(int i = 2; i < N; i++){ if(!vis[i]) prime.push_back(i); } num_prime = prime.size();}bool judge(ll x){ for(int i = 0; (ll)prime[i]*prime[i] <= x; ++i){ if(x%prime[i] == 0){ x /= prime[i]; if(x%prime[i] == 0) return false; } } return true;}int main(){ get_prime(); int T; scanf("%d",&T); while(T--){ ll n,m,ans = INF; scanf("%lld",&n); m = sqrt(n*1.0); for(ll i = m; i >= 2; --i){ if(judge(i)){ ans = n-i*i; break; } } for(ll i = m+1; i*i-n < ans; ++i){ if(judge(i)){ ans = i*i-n; break; } } printf("%lld\n",ans); } return 0;}
0 0
- BestCoder Round #85 (hdu5776,hdu5777,hdu5776)
- Bestcoder #85 1001(HDU5776)
- hdu5776
- hdu5776
- hdu5776 sum
- hdu5776 sum
- hdu5776——sum(抽屉原理)
- hdu5776 sum (鸽巢原理)
- hdu5776——sum
- Hdu5776 字串的和[鸽巢原理]
- Hdu5776 sum 抽屉原理+同余定理
- HDU5776 sum【前缀和+模除】
- hdu5777
- BestCoder Round #85 sum(尺取法)
- BestCoder Round #85
- BestCoder Round #85
- BestCoder Round #85题解
- BestCoder Round #85
- boosting
- static全局变量与普通的全局变量有什么区别?static局部变量和普通局部变量有什么区别?static函数与普通函数有什么区别?
- Caffe学习笔记(三)——Matlab接口
- 题解:整数划分问题(DP)
- Java EE笔记一
- BestCoder Round #85 (hdu5776,hdu5777,hdu5776)
- 动态规划--钢条切割问题
- 路由器
- getchar(), cin.get()
- Java EE笔记二
- 帮忙设计的一些UI
- Scrum实战读书笔记
- 第k短路
- Codeforces Round #297 (Div. 2) C. Ilya and Sticks