来来来,让我们进入算法知识的海洋~

大家好,这是我的第一篇博客,请多多支持,有些解释不清楚的地方请多多包容,好人一生平安哦~~~~谢谢!!!!!!!!!!!!!!!!!!!!!!

好的,寒暄结束!

上题目!!!!

ON1:割绳子

一面竖直的墙上钉有 n个钉子,第 i个钉子钉在距离地面 ai 米的地方,bi 米长的绳子的一端系在上面。

所有的钉子都悬挂在不同的高度上。

现在有一颗糖果同时被所有绳子的另一端绑住,要拿走糖果,需要将其降低到地面。

为此,可以割断一些绳子,一次一根。请你找到获得糖果所需割掉的最少绳子数量。

输入

第一行包含一个整数 n ( 1 ≤ n ≤ 50 ) - 钉子的数量。

接下来的 n 行中的第 i 行包含两个整数 ai 和 bi ( 1 ≤ ai , bi ≤ 200 ) - 第 i 个钉子的高度以及绑在其上的绳子的长度,所有 ai 都不同。

输出

对于每个测试用例,打印一个整数 -需要切断以使糖果落到地上的最小绳子数量。

样例输入 复制
3
4 3
3 1
1 2
样例输出 复制
2

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

思路

首先依题目所得,我们要定义变量一个整数n(表示钉子的数量),然后定义第i个钉子的高度a和绑在其上的绳子长度b,因为题目要求糖果要成功掉落就要满足高度a要大于绳子长度b,如果不满足的话糖果就不能成功掉落。为了更好的帮助理解,我就以上图进行阐述,首先如果我们先剪去最底下那根线就会发现糖果不能,这是第一步,第二步从上面的线中随意剪掉一根糖果还是不动,这就需要第三步才能成功,但是题目想要的是最少的操作,所以只用剪去上面来个高度大于绳长的线。

然后满足要求的话就要进行一次计数,这就需要再次定义一个整数来满足此要求,于是count就应运而生了,每满足要求一个就要count+1,所以这里就需要循环的加入。

好的,思路就到此结束。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

c++代码展示:
​
#include <iostream>
using namespace std;

int main(){
	int n;//钉子个数
	int a, b;//第 i 个钉子的高度以及绑在其上的绳子的长度 
	int count=0;//计数,计入第i个钉子的高度大于绑在绳子上的长度,这样就可以确保糖果可以成功掉落 
	int i=0;
	cin >> n;
	for(i=0; i < n; i++){
		cin >> a >> b;
		if(a>b)
		   count++;
	}
	cout << count;
	return 0;
} 

​

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

NO2:上上下下左右左右BABA

男枪嘴里总是念叨着一句口头禅:”上上下下左右左右BABA,哈哈哈~我有三十条命了“,现在男枪有了一个偶长度的字符串 s, 仅由小写拉丁字母'a'和'b'组成,为了使该字符串的每个偶长度的前缀中(该长度前所有字符,包括该长度对应的当前字符,组成的字符串)具有相同数量的字母'a'和'b',在一次操作中,男枪可以将某个位置上的字母替换成另一个。

例如:对于字符串 s = "abba",有2个偶长度的前缀,当长度为2时 s[1...2] = "ab", 当长度为4时s[1...4]="abba"。他们都有相同数量的'a' 和 'b';

计算男枪为了满足上述条件必须对字符串s执行的最少操作次数。

输入

输入的第一行包含一个偶数整数 n (2 ≤ n ≤ 2*105)  - 字符串 s 的长度。

输入的第二行包含长度为 n的字符串 s ,该字符串仅由小写拉丁字母'a'和'b'组成。

输出

在第一行中 输出男枪必须对字符串 s 执行的最小操作次数(可能为0)。

样例输入 复制
4
bbbb
样例输出 复制
2
提示

abba 为样例操作后的字符串(最小操作次数操作后的字符串不唯一)

最小操作次数为 2

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

思路

由题目所知,当男枪面对一个字符串的时候,他想要通过一些操作,使得字符串的每个偶数位置上的字符(从0开始)都相同,并且每个偶数长度的前缀中包含相同数量的'a'和'b'字符。

举个例子,假设有一个字符串"ababa",男枪必顫要对这个字符串进行操作,使得字符串变成"aaaba"。这样,字符串的每个偶数位置上的字符都相同(都是'a'),并且每个偶数长度的前缀中包含相同数量的'a'和'b'字符。

而我们要做的就是帮男枪计算出对于给定的字符串,他需要执行的最小操作次数是多少。通过比较字符串中相邻字符的情况,来计算操作次数。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

c++代码展示:
#include <iostream>
#include <string>
using namespace std;
int main(){
	int num, count = 0;
	cin >> num;
	string mangun;
	cin >> mangun;
	for(int i = 0; i < num; i += 2)//用于进行偶数位置字符的对比
	{
		if(mangun[i] == mangun[i + 1])
		   count++;
	}
	cout << count;
	return 0;
}

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

NO3:充满爱意的泡面

众所周知,跨年来临之际是异地情侣见面的高峰期,这段时间学校超市的泡面销量会异常升高。爱一个人就会为她舍弃全部,东软出现了一批充满爱意的泡面男孩要去校园超市购买泡面。一碗泡面要人民币5元,假如你是收银员,这些同学给你付款的面额可能是5元、10元和20元,而你要相应的找付剩余的钱给这些同学。这些同学按顺序给你付款,并且一开始你的手上没有任何零钱,请问你是否能给每位同学正确找零。给每位同学都正确的找零则返回True,否则返回False。

输入

一个整数n表示购买的顾客数量

一个n个长度的数组

输出

是否能找开,能找开返回True,不能则返回False

如:5 5 5 10 20

前 3 位顾客那里,我们按顺序收取 3 张 5 元。

第 4 位顾客那里,我们收取一张 10 元,并返还 5 元。

第 5 位顾客那里,我们找还一张 10 元和一张 5 元。

由于所有客户都得到了正确的找零,所以我们输出 True。

样例输入 复制
5
5 5 5 10 20
样例输出 复制
True

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 

思路 

结合所写的代码和题目解释如下:

这道题目描述了一个场景:超市收银员需要给购买泡面的学生正确找零,学生可能给的面额是5元、10元和20元。超市收银员需要根据购买泡面的学生的顺序依次判断是否能够正确找零。

代码中,首先读取输入的购买泡面的学生数量num和每位学生给的钱数存入数组arr中。然后使用数组a[2]来记录当前收银员手中拥有的面额,a[0]代表5元的数量,a[1]代表10元的数量。

接下来,通过遍历数组arr,根据每位学生给的钱数进行相应的处理:

如果学生给的是5元,则收银员直接收下,5元的数量加一;
如果学生给的是10元,收银员需要找零5元给学生。此时要判断手中是否有足够的5元,如果没有则无法找零,输出False;
如果学生给的是20元,收银员需要找零15元给学生,优先使用10元和5元进行找零,如果没有足够的10元和5元,则需要使用3张5元找零。如果无法找零,输出False。
最终,如果所有学生都能够得到正确的找零,则输出True;如果有任何一位学生无法得到正确的找零,则输出False。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~  

c++代码展示: 
#include <iostream>
#include <vector>
using namespace std;
int main(){
	int num, n;//num学生数量,n作用是用于临时存储每位购买泡面学生给的钱数,并将其添加到vector容器中
	cin >> num;
	vector<int> arr;
	int a[2] = {0,0};//记录5元和10元的数量 
	for(int i = 0; i < num; i++){
		cin >> n;
		arr.push_back(n);
	}
	for(auto k : arr){//使用auto关键字来声明变量k,通过for循环遍历vector容器arr中的元素。由于arr中存储的是int类型的元素,编译器可以根据这个推断k的类型为int,从而简化了代码的书写
		if(k == 5)
		    a[0] += 1;
		if(k == 10){
			a[1] += 1;
			if(a[0] >= 1)
			    a[0] -= 1;
			else{
				cout << "False" << endl;
				return 0;
			}    
		}
		if(k == 20){
			if(a[1] >= 1 && a[0] >= 1){//5元和10元的数量大于等于1张
				a[0] -= 1;
				a[1] -= 1;
			}
			else if(a[0] >= 3)//5元数量大于等于3张可以直接用5元找补
			    a[0] -= 3;
			else{
				cout << "False" << endl;
				return 0;
			}    
		}    
	}
	cout << "True" << endl;
	return 0;
} 

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~   

NO4:金铲铲之争round2

给出一组无序的数列,包含负数,写在一张纸条上,有多少种方法可以把这条纸条剪 成两片,使得一片纸条上的数字之和等于另一片纸条上的数字之和。

输入

第一行输入包含整数n(1<=n<=1e5)

第二行包含n个空格分隔的数字,这些数绝对值不超过1^5;

输出

输出解决方法的总和(两张纸片均不能为空)

样例输入 复制
9
1 5 -6 7 9 -16 0 -2 2
样例输出 复制
3

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~  

思路 

结合所写的代码和题目解释如下:

num 表示输入的数列中数字的个数,num1 用于暂存输入的数字,sum 表示整个数列的总和,sum1 表示部分数列的和,count 记录满足条件的划分方法的数量。
代码首先读取输入的数字个数 num,然后依次读取每个数字,并计算整个数列的总和,同时将数字存储在 arr 向量中。
接着通过遍历数列的每个元素(除最后一个元素外),计算当前位置之前的部分数列和,并检查剩余部分数列的和是否与之前的部分数列和相等,如果相等则满足条件,count 加一。
最后输出符合条件的划分方法的数量 count。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~分割线~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

c++代码展示:
#include<iostream>
#include<vector>
using namespace std;
int main()
{
    int num, num1, sum = 0, sum1 = 0, count = 0;
    cin >> num;
    vector<int> arr;
    for(int i = 0; i < num; i++)
    {
        cin >> num1;
        sum += num1;
        arr.push_back(num1);
    }
    for(int i = 0; i < num - 1; i++)
    {
        sum1 += arr[i];
        if(sum - sum1 == sum1)
            count += 1;
    }
    cout << count;
}

  • 25
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值