【题目荟萃】删数字、约数、黑白牛奶

删数字

时间限制:?1 Sec??内存限制:?128 MB

题目描述

奶牛在数学课上学习了整除的概念。农夫Farmer John为了考验它的数学水平,于是在白纸上写了正整数T。由于农夫不喜欢数字0,所以正整数T是不含数字0的。奶牛可以删除T的若干位数字,剩下来的数字从左到右构成一个正整数P,使得正整数P必须是5的倍数。奶牛有多少种不同的删除方案?具体请看样例解释。

?

输入

第一行,一个正整数T。

?

输出

一个整数,奶牛不同的删除方案数。
1、奶牛可以删除0个数字(即不删除任何数字)。
2、奶牛不能把T全部删除掉。即至少要剩下1位数字。
3、由于T的位数可能较长,建议用字符串形式读入。
?

?

样例输入
复制样例数据

1256
样例输出

4
?

提示

奶牛有4种不同的删除方案:
第1种方案:删除T的第四位数字,剩下的P=125,是5的倍数。
第2种方案:删除T的第一位和第四位数字,剩下的P=25,是5的倍数。
第3种方案:删除T的第二位和第四位数字,剩下的P=15,是5的倍数。
第4种方案:删除T的第一位、第二位、第四位数字,剩下的P=5,是5的倍数。

注意题目中数字范围是1-9,也就是说不可能有0的存在,我们只要寻找末位为5的位置前面有多少个数字(设为n),能么以这个5位结尾的数字种类就是2^n,然后将所有5位置前2^n相加求和就是答案
为什么是2^n,因为你从n中选择0个、1个、2个...一直选到n个,实际上就是C的公式

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<string>
#include<cmath>
#include<cstring>
#include<map>
#include<set>
#include<stack>
#include<utility>
#include<queue>
#include<vector>
#include<cctype>
using namespace std;
#define fore(i,a,b) for(int i=a;i<=b;i++)
#define forb(i,a,b) for(int i=a;i>=b;i--)
#define fir first
#define sec second
#define ABS(a) ((a)>0?(a):-(a))
typedef long long ll;
typedef long double ld;
const int MAXN=100005;
int all[100005];
int tot=0;

long long POW(int a,int x){
    long long ans=1;
    fore(i,1,x) ans*=a;
    return ans;
}

int main(){
    string s;
    cin>>s;
    fore(i,0,s.size()-1){
        if(s[i]=='5') all[++tot]=i;
    }
    long long sum=0;
    fore(i,1,tot){
        sum+=POW(2,all[i]);
    }
    cout<<sum;
    return 0;
}

约数

时间限制: 1 Sec 内存限制: 128 MB
题目描述
给出两个正整数X和Y,求X和Y的最大公约数,奶牛可以轻松解决这个问题。
农夫Farmer John决定改一改题目去考验奶牛。农夫决定询问奶牛Q个问题,每个问题的格式是这样的:
农夫给定两个正整数a和b,农夫保证a < = b,然后农夫询问奶牛:在a至b的范围内,有没有哪个整数既是X的约数同时又是Y的约数?如果有,输出最大的那个;如果没有,输出-1。

输入
第一行,两个正整数,X和Y。
第二行,一个整数数,Q。
接下来有Q行,每行两个正整数:a和b,其中保证a <= b。

输出
共Q行,每行一个整数,每行对应农夫的一个问题。

样例输入
200 120
3
9 40
25 35
10 15
样例输出
40
-1
10

提示
第一个问题:在9至40的范围内,既是200的约数,同时又是120的约数,共有3个,分别是:10,20,40,在3个之中,40最大,所以输出40。
第二个问题:在25至35的范围内,找不到既是200的约数,同时又是120的约数,所以输出-1。
第三个问题:在10至15的范围内,既是200的约数,同时又是120的约数,只有10,所以输出10。

1、对于40%的数据,1<=X<=100,1 <= Y <= 100, 1 <= Q <= 100,1<=a<b<=100
2、对于100%的数据,1<=X<=1000000000,1 <= Y <= 1000000000, 1 <= Q <= 30000,1<=a<b<=1000000000。

先将所有约数筛选出来排序,每次选择的时候倒序遍历约数看是否有符合要求的约数,否则输出-1

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<string>
#include<cmath>
#include<cstring>
#include<map>
#include<set>
#include<stack>
#include<utility>
#include<queue>
#include<vector>
#include<cctype>
using namespace std;
#define fore(i,a,b) for(int i=a;i<=b;i++)
#define forb(i,a,b) for(int i=a;i>=b;i--)
#define fir first
#define sec second
#define ABS(a) ((a)>0?(a):-(a))
typedef long long ll;
typedef long double ld;
const int MAXN=100005;
vector<long long>v;

int main(){
    long long a,b;
    cin>>a>>b;
    if(a>b) swap(a,b);
    int t=sqrt(double(a));
    fore(i,1,t){
        if(a%i==0){
            if (b % i == 0) v.push_back(i);
            if(i*i!=a) if(b%(a/i)==0) v.push_back(a/i);
        }
    }
    sort(v.begin(),v.end());
    //fore(i,0,v.size()-1) printf("%lld ",v[i]);
    //cout<<endl;
    int k;cin>>k;
    long long x,y;
    fore(i,1,k){
        scanf("%lld%lld",&x,&y);
        bool flag=true;
        forb(j,v.size()-1,0) if(v[j]<=y && v[j]>=x) {printf("%lld\n",v[j]);flag=false;break;}
        if(flag) printf("-1\n");
    }
    return 0;
}

黑白奶牛

时间限制: 1 Sec 内存限制: 128 MB
题目描述
有N只奶牛从左往右排成一行,编号是1至N。这N只奶牛当中,有一些奶牛是黑色的,其余的是白色的。
color[i]表示第i只奶牛的颜色,如果color[i]=0则表示第i头奶牛是黑色的,如果color[i]=1则表示第i头奶牛是白色的。
六一奶牛儿童节快到了,农场主Farmer John要从这N头奶牛当中,挑选尽可能多的奶牛去参加晚会。
Farmer John挑选奶牛的原则是:挑选编号是连续的一段奶牛,这一段奶牛的颜色必须全部是白色的。
Farmer John有一个魔法棒,每用一次魔法棒就可以把一头黑色的奶牛变成一头白色的奶牛,魔法棒最多只能使用K次。
在上述条件下,最多可以有多少头奶牛去参加晚会呢?

输入
第一行,两个整数,N和K。
第二行,N个整数,第i个整数就是color[i],color[i]要么是0,要么是1。

输出
一个整数,表示最多有多少头奶牛可以去参加晚会。

样例输入
复制样例数据
11 0
1 1 0 0 1 1 1 1 0 1 1
样例输出
4

提示
由于K=0,所以不能使用魔法棒,所以挑选编号是5至8的奶牛去参加晚会。

对于50%的数据,1 <= N <= 1000,K = 0,即不能使用魔法棒。
对于100%的数据,1 <= N <= 100000, 1 <= K <=N。

我用的是尺取法,然后将k=0的特殊情况单独找最大连续1的子序列数目,尺取法的话就是不断向右扩展,如果遇到0,k--,如果k==0,左侧向右,看能否k++;

#include <algorithm>
#include <cctype>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <stack>
#include <string>
#include <utility>
#include <vector>
using namespace std;
#define fore(i, a, b) for (int i = a; i <= b; i++)
#define forb(i, a, b) for (int i = a; i >= b; i--)
#define fir first
#define sec second
#define ABS(a) ((a) > 0 ? (a) : -(a))
typedef long long ll;
typedef long double ld;
const int MAXN = 100005;
int nums[MAXN];

int main() {
    int n, k;
    cin >> n >> k;
    fore(i, 1, n) {
        scanf("%d", &nums[i]);
    }
    int l = 1, r = 1, tmpk, ans = 0;
    if (k == 0) {
        int tmpans = 0;
        fore(i, 1, n) {
            if (nums[i] == 1) {
                if (nums[i] == nums[i - 1])
                    tmpans++, ans = max(tmpans, ans);
                else
                    tmpans = 1, ans = max(tmpans, ans);
            }
        }
    } else {
        while (r <= n) {
            if (nums[r])
                r++, ans = max(ans, r - l);
            else {
                if (k > 0)
                    k--, r++, ans = max(ans, r - l);
                else if (nums[l])
                    l++;
                else
                    l++, k++;
            }
        }
    }
    cout << ans;
    return 0;
}

原文地址:https://www.cnblogs.com/rign/p/10351586.html

时间: 2024-08-30 09:25:09

【题目荟萃】删数字、约数、黑白牛奶的相关文章

删数字 -- 2016华为笔试题

题目: 有一个整型数组a[n]顺序存放0 ~ n-1,要求每隔两个数删掉一个数,到末尾时循环至开头继续进行,求最后一个被删掉的数的原始下标位置. 以 8 个数(n=8)为例:{0,1,2,3,4,5,6,7}, 0->1->2(删除)->3->4->5(删除)->6->7->0(删除),如此循环直到最后一个数被删除. 思路: 这题有3种解法, 第一种就是构建循环链表模拟删数字的过程,但是时间空间复杂度较高, 第二种是用LinkedList模拟删数字过程,相较

九度oj 题目1349:数字在排序数组中出现的次数

题目描述: 统计一个数字在排序数组中出现的次数. 输入: 每个测试案例包括两行: 第一行有1个整数n,表示数组的大小.1<=n <= 10^6. 第二行有n个整数,表示数组元素,每个元素均为int. 第三行有1个整数m,表示接下来有m次查询.1<=m<=10^3. 下面有m行,每行有一个整数k,表示要查询的数. 输出: 对应每个测试案例,有m行输出,每行1整数,表示数组中该数字出现的次数. 样例输入: 8 1 2 3 3 3 3 4 5 1 3 样例输出: 4 使用库函数即可解决

九度_题目1349:数字在排序数组中出现的次数

//用map来实现总是超出最大的内存限制 题目描述: 统计一个数字在排序数组中出现的次数. 输入: 每个测试案例包括两行: 第一行有1个整数n,表示数组的大小.1<=n <= 10^6. 第二行有n个整数,表示数组元素,每个元素均为int. 第三行有1个整数m,表示接下来有m次查询.1<=m<=10^3. 下面有m行,每行有一个整数k,表示要查询的数. 输出: 对应每个测试案例,有m行输出,每行1整数,表示数组中该数字出现的次数. 样例输入: 8 1 2 3 3 3 3 4 5 1

[Jobdu] 题目1544:数字序列区间最小值

题目描述: 给定一个数字序列,查询任意给定区间内数字的最小值. 输入: 输入包含多组测试用例,每组测试用例的开头为一个整数n(1<=n<=100000),代表数字序列的长度.接下去一行给出n个数字,代表数字序列.数字在int范围内.下一行为一个整数t(1<=t<=10000),代表查询的次数.最后t行,每行给出一个查询,由两个整数表示l.r(1<=l<=r<=n). 输出: 对于每个查询,输出区间[l,r]内的最小值. 样例输入: 5 3 2 1 4 3 3 1

【题目荟萃】换位置游戏

换位置游戏 时间限制: 1 Sec 内存限制: 128 MB 题目描述 N 个小朋友(编号为 1 到 N)正在玩一个换位置游戏.从左到右依次排列着 N 个凳子 (编号为 1 到 N,最左边的为 1 号凳子,最右边的为 N 号凳子),每个凳子上都有一个数字 (凳脚处红色数字),每个数字互不相同,且都是不超过 N 的正整数. 每轮游戏每个小朋友会做到凳子所写的数字的编号的凳子,求最小轮数让所有人坐到跟自己编号一样的凳子: 输入 输入共 2 行. 第 1 行是一个整数 N(1≤N≤1000),表示参加

每日一九度之 题目1089:数字反转

时间限制:1 秒 内存限制:32 兆 特殊判题:否 提交:3452 解决:1892 题目描述: 12翻一下是21,34翻一下是43,12+34是46,46翻一下是64,现在又任意两个正整数,问他们两个数反转的和是否等于两个数的和的反转. 输入: 第一行一个正整数表示测试数据的个数n. 只有n行,每行两个正整数a和b(0<a,b<=10000). 输出: 如果满足题目的要求输出a+b的值,否则输出NO. 样例输入: 2 12 34 99 1 样例输出: 46 NO //Asimple #incl

九度OJ—题目1089:数字反转

题目描述: 12翻一下是21,34翻一下是43,12+34是46,46翻一下是64,现在又任意两个正整数,问他们两个数反转的和是否等于两个数的和的反转. 输入: 第一行一个正整数表示测试数据的个数n. 只有n行,每行两个正整数a和b(0<a,b<=10000). 输出: 如果满足题目的要求输出a+b的值,否则输出NO. 样例输入: 2 12 34 99 1 样例输出: 46 NO 来源: 2005年上海交通大学计算机研究生机试真题 答疑: 解题遇到问题?分享解题心得?讨论本题请访问:http:

九度oj 题目1051:数字阶梯求和

题目描述: 给定a和n,计算a+aa+aaa+a...a(n个a)的和. 输入: 测试数据有多组,输入a,n(1<=a<=9,1<=n<=100). 输出: 对于每组输入,请输出结果. 样例输入: 1 10 样例输出: 1234567900 这道题的难点在于处理很长很长的数的求和 1 #include <cstdio> 2 #include <cstdlib> 3 #include <cstring> 4 #include <string&

[转]as3 算法实例【输出1 到最大的N 位数 题目:输入数字n,按顺序输出从1 最大的n 位10 进制数。比如输入3,则输出1、2、3 一直到最大的3 位数即999。】

思路:如果我们在数字前面补0的话,就会发现n位所有10进制数其实就是n个从0到9的全排列.也就是说,我们把数字的每一位都从0到9排列一遍,就得到了所有的10进制数. 1 /** 2 *ch 存放数字 3 *n n位数 4 *index 计数值 5 **/ 6 private function num(ch:Array,n:int,index:int):void 7 { 8 if(index==n) 9 { 10 trace(ch); 11 return; 12 } 13 for(var i:in