【PTA】PAT (Advanced Level) Practice 1007-1010(语言C++)

思路都在代码注释中。

1007 Maximum Subsequence Sum

Given a sequence of K integers
在这里插入图片描述
A continuous subsequence is defined to be
在这里插入图片描述
where 1≤i≤j≤K. The Maximum Subsequence is the continuous subsequence which has the largest sum of its elements. For example, given sequence { -2, 11, -4, 13, -5, -2 }, its maximum subsequence is { 11, -4, 13 } with the largest sum being 20.

Now you are supposed to find the largest sum, together with the first and the last numbers of the maximum subsequence.

Input Specification:
Each input file contains one test case. Each case occupies two lines. The first line contains a positive integer K (≤10000). The second line contains K numbers, separated by a space.

Output Specification:
For each test case, output in one line the largest sum, together with the first and the last numbers of the maximum subsequence. The numbers must be separated by one space, but there must be no extra space at the end of a line. In case that the maximum subsequence is not unique, output the one with the smallest indices i and j (as shown by the sample case). If all the K numbers are negative, then its maximum sum is defined to be 0, and you are supposed to output the first and the last numbers of the whole sequence.

Sample Input:

10
-10 1 2 3 4 -5 -23 3 7 -21

Sample Output:

10 1 4

翻译:

找出在第二行中最大的连续子序列和,以及最大的连续子序列的第一个最后一个数字
如果最大子序列不唯一,则输出具有最小索引i和j的子序列。
如果所有的数都是负的,那么它的最大和被定义为0,你应该输出整个序列的第一个和最后一个数字。

代码:

思路都在代码注释中。

#include <iostream>
#include <vector>
using namespace std;
int main()
{
    
    
    int k;
    cin>>k;
    vector<int> a(k);
    
    //首尾元素的下标
    int left=0,right = k-1;
    
    //sum是临时加和,maxsum是最终的加和,tempindex是left的临时下标
    int sum=0, maxsum=-1, tempindex = 0;
    
    for(int i = 0;i < k; i++){
    
    
        //输入数据
        cin>>a[i];
        sum = sum + a[i];
        
        //当sum小于0,再加其他数字都还是会拉低数值,所以直接舍弃
        if(sum < 0){
    
    
            sum = 0;
            tempindex = i + 1;
        }
        //只有当sum大于0且大于maxsum(等于maxsum,取前者)的情况,maxsum才更新,
        else if(sum > maxsum){
    
    
            maxsum = sum;
            left = tempindex;
            right = i;
        }
    }
    if(maxsum < 0) maxsum = 0;
    cout << maxsum << " " << a[left] << " " << a[right];
    return 0;
}

1008 Elevator

The highest building in our city has only one elevator. A request list is made up with N positive numbers. The numbers denote at which floors the elevator will stop, in specified order. It costs 6 seconds to move the elevator up one floor, and 4 seconds to move down one floor. The elevator will stay for 5 seconds at each stop.

For a given request list, you are to compute the total time spent to fulfill the requests on the list. The elevator is on the 0th floor at the beginning and does not have to return to the ground floor when the requests are fulfilled.

Input Specification:
Each input file contains one test case. Each case contains a positive integer N, followed by N positive numbers. All the numbers in the input are less than 100.

Output Specification:
For each test case, print the total time on a single line.

Sample Input:

3 2 3 1

Sample Output:

41

翻译:

我们城市最高的建筑只有一个电梯。请求列表由N个正数组成。这些数字表示电梯将停在几层,按特定的顺序排列。电梯上一层需要6秒,下一层需要4秒。电梯在每一站停留5秒。

对于给定的请求列表,要计算完成列表上的请求所花费的总时间。电梯在开始时位于第0层,当请求得到满足时不需要返回到底层。

代码:

#include <iostream>
using namespace std;
int main()
{
    
    
    int a,now = 0,time = 0;
    cin>>a;
    while(cin>>a){
    
    
        //上升
        if(a>now){
    
    
            time = time + 6*(a-now);
        }
        //下降
        else{
    
    
            time = time + 4*(now-a);
        }
        now = a;
        time += 5;//停下来的时间
    }
    cout<<time;
}

1009 Product of Polynomials

This time, you are supposed to find A×B where A and B are two polynomials.

Input Specification:
Each input file contains one test case. Each case occupies 2 lines, and each line contains the information of a polynomial:
在这里插入图片描述

Output Specification:
For each test case you should output the product of A and B in one line, with the same format as the input. Notice that there must be NO extra space at the end of each line. Please be accurate up to 1 decimal place.

Sample Input:

2 1 2.4 0 3.2
2 2 1.5 1 0.5

Sample Output:

3 3 3.6 2 6.0 1 1.6

翻译:

给出两个多项式A和B,求A*B的结果。
输入样例:

有几项 指数1 对应的系数1 指数2 对应的系数2。。。

要求输出:

有几项系数不为零 逐个输出结果的指数和对应系数

代码:

#include<iostream>
#include <iomanip>
using namespace std;
int main()
{
    
    
    double b, arr[1004]={
    
    0.0} , ans[2001]={
    
    0.0};
    int n1 , n2 , a , cnt=0;
    cin>>n1;
    //输入第一行数据
    for( int i=0 ; i < n1 ; i++ ){
    
    
        cin >> a >> b;
        arr[a] = b;
    }
    //输入第二行数据
    cin>>n2;
    for( int i=0 ; i < n2 ; i++ ){
    
    
        cin >> a >> b;
        //逐项相乘,然后将系数加起来,放入ans数组
        for( int j=0 ; j < 1001 ; j++ ){
    
    
            ans[ j + a ] += arr[ j ] * b;
        }
    }
    //数系数不为0有几项
    for(int i=2000 ; i>=0; i--){
    
    
        if(ans[i]!=0.0)
            cnt++;
    }
    cout<<cnt<<" ";
    //输出系数,逆着输出
    int flag=0;
    for(int i=2000 ; i>=0; i--){
    
    
        if( ans[i]!=0.0 ){
    
    
            cout<< i << setiosflags(ios::fixed)<<setprecision(1) << " " << ans[i];
            flag++;
        }
        //最后一项不输出空格
        if(ans[i]!=0.0 && flag!=cnt)
            cout<<" ";
    }
}

1010 Radix

在这里插入图片描述

翻译:

对于任意一对正整数n1和n2,你的任务是找出一个数的基数,而另一个数的基数是已知的。

输入规范:
每个输入文件包含一个测试用例。每一行包含4个正整数:N1 N2 标签 基数。
这里N1和N2都不超过10位数字。一个数字小于它的基数,从集合{0-9,A -z}中选择,其中0-9表示十进制数0-9,A -z表示十进制数10-35。如果标签是1,最后一个基数是N1的基数,如果标签是2,最后一个基数是N2的基数。

输出要求:
对于每个测试用例,在一行中打印另一个数字的基数,这样等式N1 = N2就为真。
如果这个等式是不可能的,那就输出不可能
如果解不唯一,则输出可能的最小基数

代码:

#include<iostream>
#include<cmath> //pow()
#include<cctype>
#include<algorithm>
#include<iomanip> //保留一位
using namespace std;

//给一个数值和进制,将数值转化为10进制
long long convert(string n, long long radix){
    
    
    long long sum = 0;
    int index = 0, temp = 0;
    //auto是C语言的一个关键字,关键字主要用于声明变量的生存期为自动
    //rbegin(),rend()反向迭代器
    for(auto it = n.rbegin() ; it != n.rend(); it++){
    
    
        
        //二进制有0-9,a-z,字母要转化成数字
        temp = isdigit(*it) ? *it -'0' : *it -'a' + 10;
        
        //pow(x,y)用来求 x 的 y 次方的值
        sum += temp * pow(radix , index++);
    }
    return sum;
}

//二分查找法,找到令两个数值相等的进制数
long long find_radix(string n,long long num){
    
    
    char it = *max_element(n.begin(),n.end());//查询最大值所在的第一个位置
    long long low = (isdigit(it)? it-'0' : it -'a' + 10) +1;
    long long high = max(num, low);
    while(low  <= high){
    
    
        long long mid = (low + high)/2;
        long long t = convert(n,mid); //要找的值
        
        if (t<0 || t>num) high = mid - 1;
        else if (t == num) return mid; //找到
        else low = mid +1;
    }
    return -1; //找不到
}

int main()
{
    
    
    string s1, s2;
    long long tag = 0, radix = 0, result_radix;
    cin>> s1 >> s2 >> tag >> radix;
    
    //已知的数的基数是第一个数的基数?是则将s1转化为10进制后比较,不是则将s2转化为10进制后比较
    result_radix = tag == 1 ? find_radix(s2, convert(s1 , radix)) :find_radix(s1, convert(s2 , radix));
    
    //输出
    if(result_radix == -1){
    
    
        cout<<"Impossible";
    }else{
    
    
        cout<<setiosflags(ios::fixed)<<setprecision(1)<<result_radix;
    }
    return 0;
}

END

猜你喜欢

转载自blog.csdn.net/qq_51669241/article/details/124913651