在本周博主做的四道算法题中选出两道算法题进行思路的讲解(仅仅是一种解题方式),博主的代码有点多,如有更好的解题思路或代码,欢迎发到评论区
1.Candies
本题意思是:有两种法术,一种是2x+1,一种是2x-1,初始的糖果数目为1,输入你想获得的糖果数目,如果能通过有限次(<=40) 的法术来获得需要数目的糖果,先输出使用的法术次数,在换行依次输出使用的是哪个法术;若不能的到所需的糖果数目,就输出-1
大体思路
无论是法术1还是法术2,只能获得数目为奇数的糖果,数目为偶数时,输出-1
对于奇数的糖果进行法术的分配,列两个方程,2x-1和2x+1,哪个法术算出x为奇数,则用的哪个法术
注意事项
由于我们是从后往前算的,所以计算出的法术顺序是反的,需要从前向后输出才是正确的
现在我们开始逐步实现代码
#include<iostream>
#include<vector>
using namespace std;
int main()
{
//我们需要的几个测试对象
int n = 0;
cin >> n;
//法术1
int count1 = 0;
//法术2
int count2 = 0;
int y = 0;
//elem存放我们需要的糖果数目
vector<int>elem;
//pell存放达到所需数目糖果的法术
vector<int>pell;
//count存放我们使用法术的次数
vector<int>count;
//输入我们需要的糖果数目,将其依次插入elem中
for (int i = 0; i < n; i++)
{
int candies = 0;
cin >> candies;
elem.push_back(candies);
}
}
博主实现法术1的方式是
((j + 1) / 2) % 2 != 0
法术2
((j - 1) / 2) % 2 != 0
需要注意的是当j=2时,式子也成立,所以还需要加入限制条件
如果式子成立,就将1或者2插入pell中
for (j = elem[i]; j > 1;)
{
if (((j + 1) / 2) % 2 != 0 && j % 2 != 0)
{
j = (j + 1) / 2;
pell.push_back(1);
count1++;
}
else if (((j - 1) / 2) % 2 != 0 && j % 2 != 0)
{
j = (j - 1) / 2;
pell.push_back(2);
count2++;
}
else if (j % 2 == 0)
break;
}
接下来开始判断糖果的数目是否能用法术1和法术2表示
因为我们的count是一个连续的数列,为了不影响操作,当糖果的数目为偶数的时候,将0插入
这里有一个坑,如果我们不管这个偶数糖果的count,如果输入中间有零的糖果数,就会出现错误,如:3,4,5,6,7,8,9
if (elem[i] % 2 == 0)
{
count.push_back(-1);
cout << count[i] << endl;
count[i] = 0;
}
else
{
count.push_back(count1 + count2);
cout << count[i] << endl;
int y = 0;
for (int a = 0; a < i; a++)
{
y += count[a];
}
if (i == 0)
{
for (int x = count[i]-1; x>=0 ; x--)
cout << pell[x] << " ";
cout << endl;
}
else
{
if(i==1)
y = count[0];
int x = count[i] + y - 1;
for (x; x >= y; x--)
cout << pell[x] << " ";
cout << endl;
}
}
需要注意的是,y的值应该在x的前面被赋予
2.Lucky Numbers
题目大意:给定两个数,在这个区间内,将所有数中的最大数字和最小数字相减,输出差值最大的那个数
思路:将一个数字拆分,用%10后/10的操作来实现,求出最大数字和最小数字,将两个数字的差值存入容器中,使用find函数返回最大值的下标,便于我们输出原数
我们使用了max_element和min_element,它们是<algorithm>中的库函数,用于返回最大值和最小值的地址max_element(begin,end)
#include<iostream>
#include<vector>
#include<algorithm>
#include<cmath>
using namespace std;
int main()
{
int n(0);
cin >> n;
int f = 0;
int l = 0;
vector<int>array;
vector<int>first;
vector<int>last;
vector<int>all;
vector<int>a;//存储最大数字和最小数字的差值
for (int i = 0; i < n; i++)
{
cin >> f;
first.push_back(f);
cin >> l;
last.push_back(l);
}
int m = 0;
for (int j = 0; j < n; j++)
{
m = 0;
for (int i = first[j]; i <= last[j]; i++)
{
all.push_back(i);
int d = i;
while (d > 0)
{
array.push_back(d % 10);
d /= 10;
}
int max = *max_element(array.begin(), array.end());
int min = *min_element(array.begin(), array.end());
a.push_back(max - min);
array.clear();
m++;
}
int max = *max_element(a.begin(), a.end());
int c = find(a.begin(), a.end(), max) - a.begin();
cout << all[c] << endl;
all.clear();
a.clear();
//b.clear();
}
return 0;
}