软件设计期末oj题目

本文介绍了六个编程题目,包括找出科学家“同在”的最多时期、数组中找和为目标值的数对、链表大数相加、最少切割法棍次数、最短路径问题以及打印机隐藏信息的解析。每个题目都提供了C++代码实现,涵盖了算法和数据结构的应用。
摘要由CSDN通过智能技术生成

题目1【科学盛世】

某个杂志的主编想要找出最多的卓越科学家在世的年代。现在他的手上有这些科学家的出生与去世的年份(byear,eyear);如果某两个科学家的年份有交叉(10年以上,即一个的 eyear-另一个的 byear>=10),认为两人是“同在”,科学家同在最多的时代,称为“科学盛世”(一个科学家,只要跟另一个同在即可,而不是跟所有的都同在),请找出这个盛世的开始年和结束年。

#include<bits/stdc++.h>
using namespace std;
typedef struct life{
    int byear,eyear;
}life;
life p[1001];
bool compare(life p1, life p2)
{
    if(p1.byear!=p2.byear)
        return p1.byear<p2.byear;
    else
        return p1.eyear<p2.eyear;
}
int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        cin>>p[i].byear>>p[i].eyear;
    }
    sort(p,p+n,compare);
    int startYear,endYear;
    startYear = p[0].byear;
    endYear = p[0].eyear;
    int max =1;
    for(int i=0;i<n-1;i++)
    {
        int sy = p[i].byear,ey=p[i].eyear;
        int num = 1;
        for(int j=i+1;j<n;j++)
        {
            if(j==(n-1)&&(p[i].eyear-p[j].byear)>=10)
            {
                ey = p[j].eyear;
            }
            if((p[i].eyear-p[j].byear)>=10)
            {
                num++;
            }
            else
            {
                ey = p[j-1].eyear;
                break;
            }
        }

        if (num>max)
        {
            startYear = sy;
            endYear = ey;
            max = num;
        }
        else if(num == max)
        {
            if(endYear>sy)
                endYear = ey;
        }
    }
    cout<<startYear<<" "<<endYear<<endl;
    return 0;
}

题目2【找两数】

给定一个整数的数组,找出这样的两个数,这两个整数的和加起来等于一个特定的整数 target,输出这样的数对。要求尽可能降低复杂度。
提示:哈希方法或其他方法。

#include<bits/stdc++.h>
using namespace std;
int main()
{
    int n,target,nums[1001];
    int sum=0;
    cin>>n>>target;
    for(int i=0;i<n;i++)
    {
        cin>>nums[i];
    }
    for(int i=0;i<=n/2;i++)
        for(int j=i+1;j<n;j++)
    {
        if(nums[i]+nums[j]==target&&i!=j&&i<j&&nums[i]>0&&nums[j]>0)
            {cout<<nums[i]<<" "<<nums[j]<<endl;
            nums[i]=0;
            nums[j]=0;
            sum+=1;}
    }
    if(sum==0)
        cout<<"0"<<" "<<"0"<<endl;
    return 0;
}

题目3 【大数相加】

两组数据,要求使用结构体链表表示,每个节点只放一个数字:
struct ListNode {
int val;
struct ListNode *next;
};
Input: (2->4->3)+(5->6->4)
Output: 7->0->8
在这里插入图片描述

#include<bits/stdc++.h>
using namespace std;
typedef struct node {
    int val;
    node* next;
}Node;
int main()
{
    Node *a,*b,*p1,*p2,*t;
    a = new Node;b = new Node;
    string s;
    cin >> s;
    p1 = a;p2 = b;
    bool flag = true;
    for (int i = 0;i < s.length();i++)
    {
        char c = s[i];
        if (c == '+')
            flag = false;
        if ('0' <= c && c <= '9')
        {
            int val = c - '0';
            t = new Node;
            t->val = val;
            t->next = NULL;
            if (flag) {
                p1->next = t;
                p1 = t;
            }
            else {
                p2->next = t;
                p2 = t;
            }
        }
    }
    Node* res,*p3;
    res = new Node;
    p1 = a->next;p2 = b->next;p3 = res;
    int c = 0;
    int num;
    while (p1!=NULL && p2!=NULL)
    {
        t = new Node;
        num = p1->val + p2->val + c;
        t->val = num % 10;
        c = num / 10;
        t->next = NULL;
        p3->next = t;
        p3 = t;
        p1 = p1->next;p2 = p2->next;
    }
    while (p1 != NULL) {
        t = new Node;
        num = p1->val + c;
        t->val = num % 10;
        c = num / 10;
        t->next = NULL;
        p3->next = t;
        p3 = t;
        p1 = p1->next;
    }
    while (p2 != NULL) {
        t = new Node;
        num = p2->val + c;
        t->val = num % 10;
        c = num / 10;
        t->next = NULL;
        p3->next = t;
        p3 = t;
        p2 = p2->next;
    }
    if (c != 0)
    {
        t = new Node;
        t->val = c;
        t->next = NULL;
        p3->next = t;
        p3 = t;
    }
    p3 = res->next;
    while (p3->next != NULL) {
        cout << p3->val<<"->";
        p3 = p3->next;
    }
    cout << p3->val << endl;
    return 0;
}

题目4 【砍几刀】

一根长度为 n 个单位的法棍,要切成长度为 1 的小段;一次可以同时切任意根,请输出切割所需要的最小次数。

#include<bits/stdc++.h>
using namespace std;
int main()
{
    int n,num;
    cin>>n;
    int len = 1;
    for(num=0;;num++){
        if(len>n) break;
        len = len*2;
    }
    cout<<num<<endl;
    return 0;
}

题目5 【走路的学问】

如图:A 到 B 的街区尺寸为 4*5。A 为左上,B 为右下,从 A 走到 B,只能向右或向下走,不绕路。输入 A 点和 B 点的坐标,如果街区之间的代价不一样,怎么求最短路径?
在这里插入图片描述

#include<bits/stdc++.h>
using namespace std;
typedef struct node {
    int val;
    node* next;
}Node;
int xval[100][100], yval[100][100];
int n;

int findmin(int x, int y) {
    if (x == n - 1 && y == n - 1)
        return 0;
    else if (x == n - 1) {
        return findmin(x, y + 1) + xval[x][y];
    }
    else if (y == n - 1) {
        return findmin(x + 1, y) + yval[x][y];
    }
    else {
        return min(findmin(x + 1, y) + yval[x][y], findmin(x, y + 1) + xval[x][y]);
    }
}

int main()
{
    cin >> n;
    int i = 0, j = 0;
    for (i = 0;i < 2 * n - 1;i++)
    {
        int num;
        if (i % 2 == 0)//输入xval
        {
            for (j = 0;j < n - 1;j++) {
                cin >> num;
                xval[i / 2][j] = num;
            }
        }
        else//输入yval
        {
            for (j = 0;j < n;j++) {
                cin >> num;
                yval[i / 2][j]=num;
            }    
        }
    }
    int res = findmin(0, 0);
    cout << res << endl;

    //cout << min(13, 435);


/**
    for (i = 0;i < n;i++)
    {
        for (j = 0;j < n - 1;j++)
            cout << xval[i][j] << " ";
        cout << endl;
    }

    cout << endl;
    for (i = 0;i < n-1;i++)
    {
        for (j = 0;j < n;j++)
            cout << yval[i][j] << " ";
        cout << endl;
    }
    **/
    return 0;
}

题目6【打印机的秘密】

很多打印机隐藏着某些信息,这些信息多数并没有对外开放。比如下面左图的打印内容中,包含了一些黄色的点,这些点表示了某些信息,一般情况下不会被注意到;如果采用伪色彩增强的方法,我们可以将其转换成右图,这样看起来更明显。

下面是Xerox DocuColor series的信息格式描述:
Xerox Docucolor Matrix
Below is a representations of the DocuColor matrix printed on each sheet, and how they might be interpreted. The fingerprint is a 8 row x 15 column matrix of yellow dots. Note on the drawing that they number columns starting at index 1.
The first row and first column are special. They represent a property called parity which we will discuss in a moment. Otherwise:
● columns 2 and 5 represent time (minutes and hours respectively)
● columns 6, 7, 8 represent a date
● columns 11, 12, 13, 14 represent a serial number
● columns 3,4,9,10,15 are ignored (reserved).

In the figure, the two rows at the bottom are not part of the matrix but are the interpretation of the columns for your benefit. Each row represents a power of two, and so each column represents a decimal number. Look at column 2. There is a dot in the row representing 2, 16 and
32. The sum of those is 50, which represents the minutes in the time. Notice we do not count the top row, the parity row, in any calculation. For column 5, there is a dot at 4 and 8, representing 12 hours. Thus the time this page was printed was 12:50. The other interpretations are done in
the same manner. Note that, for our purposes, we would interpret all of the serial number columns, so our expectation would be to print the serial number as 21052857 in that order.
Parity is a really easy concept to understand. We typically use parity on binary representations such as a binary string. To determine the parity of a binary string, you count the number of 1’s that occur in the string. If the 1’s count is even, then the parity for that string is 1, if the 1’s count is odd then the parity is 0.
Row 1 has its parity bit set (1). The row has 6 dots, even parity. The bit accurately represents the parity of the row. Row 8 has 5 dots, odd parity, value of 0, no dot. The only weird one is the top left corner. Does that represent the parity of the first column (all the
row parities) or the first row (the parity of all the columns). Has to be the parity of the column.
In the image above, For the column parity in column 2,representing a parity of 0. If we count the number of 1’s in the column there are three dots (three 1’s), so the parity is odd. The parity bit accurately reflects the parity of the column. Columns 3 and 4 have no dots. The parity of 0 is 1, so 3 and 4 are set to 1 (a dot). Column 5 has two dots (two 1’s), the parity is even, so the parity is 1 (a dot).
We cannot actually read the dots, so instead we read a file of the following form (this file representing dot patterns used in the image above).
1 0 1 1 1 0 1 1 1 0 1 0 1 0 1
1 0 0 0 0 0 0 0 0 1 0 0 0 0 1
1 1 0 0 0 0 0 0 0 1 1 0 0 0 1
1 1 0 0 0 1 0 0 0 1 1 1 0 1 0
0 0 0 0 1 0 0 0 0 1 1 1 0 0 1
0 0 0 0 1 1 1 1 0 1 0 1 1 1 1
0 1 0 0 0 0 1 0 0 1 0 0 0 0 0
1 0 0 0 0 1 0 1 0 1 1 0 1 1 0

要求:采用面向对象编程,提供构造函数、校验判断(校验码和实际数值是否一致)获取日期、时间、序列号等等成员函数。
思路:对应列求和即可
在这里插入图片描述

#include<bits/stdc++.h>
using namespace std;
class Solution {
public:
    int data [8][15];
    int info(int col);
    void show();
    Solution(int data[8][15]);
    void showdata();
};

int Solution:: info(int col) {
    int sum = 0;
    for (int i = 1;i < 8;i++) {
        if (data[i][col] == 1) {
            
            int s = pow(2, 7 - i);
            sum += s;
        }
    }
    return sum;
}

void Solution::show() {
    printf("%02d%02d-%02d-%02d\n", 20, info(7), info(6), info(5));
    printf("%02d:%02d\n", info(4), info(1));
    printf("%02d%02d%02d%02d\n", info(13), info(12), info(11), info(10));
}

Solution::Solution(int a[8][15]) {
    for (int i = 0;i < 8;i++)
        for (int j = 0;j < 15;j++)
            data[i][j] = a[i][j];
}

void Solution::showdata() {
    for (int i = 0;i < 8;i++)
    {
        for (int j = 0;j < 15;j++)
        {
            cout << data[i][j];
        }
        cout << endl;
    }
}

int main()
{
    int data1[8][15];
    for (int i = 0;i < 8;i++) {
        for (int j = 0;j < 15;j++) {
            cin >> data1[i][j];
        }
    }    
    Solution demo = Solution(data1);
    demo.show();
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Andy-wen

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值