吉林大学2023数据结构上机3

区间最小值I
分数 100
作者 谷方明
单位 吉林大学
对N个整数的序列,从左到右连续查询 M 长度子序列 A 
i

 ,A 
i+1

 ,...,A 
i−M+1

  (1≤i,M≤N)的最小值。

输入格式:
第1行,两个整数:N和M,表示整数的个数和区间长度,1≤N≤100000.
第2行,N个整数,每个整数x 都满足 │x│≤2000000000。

输出格式:
1行, 用空格分隔的N-M+1个整数,对应从左到右所有连续M长度子序列的最小值。

输入样例:
6  3 
1 2 5 3 4 6
输出样例:
1 2 3 3


#include <stdio.h>
long long x[100000][2];
int main(void)
{
    long long n, m, a, b, c = 0, d = 0, i;
    scanf("%lld %lld", &n, &m);
    for (a = 0; a < n; a++)
    {
        scanf("%lld", &i);
        for (b = c; b >= 0; b--)    //单调性维护
        {
            if (b == d || i > x[b - 1][0])
            {
                x[b][0] = i;
                x[b][1] = a;
                c++;
                break;
            }
            else
            {
                x[b - 1][0] = 0;
                x[b - 1][1] = 0;
                c--;
            }
        }
        if (x[c - 1][1] - x[d][1] >= m)     //区间维护
        {
            x[d][1] = 0;
            x[d][0] = 0;
            d++;
        }
        if (a + 1 >= m)
        {
            if(n-a!=1)
            printf("%lld ", x[d][0]);
            else
                printf("%lld", x[d][0]);
        }
    }
}

森林的层次遍历
分数 100
作者 谷方明
单位 吉林大学
给定一个森林F,求F的层次遍历序列。森林由其先根序列及序列中每个结点的度给出。

输入格式:
第1行,1个整数n,表示森林的结点个数, 1≤n≤100000.

第2行,n个字符,用空格分隔,表示森林F的先根序列。字符为大小写字母及数字。

第3行,n个整数,用空格分隔,表示森林F的先根序列中每个结点对应的度。

输出格式:
1行,n个字符,用空格分隔,表示森林F的层次遍历序列。

输入样例:
在这里给出一组输入。例如:

14
A B C D E F G H I J K L M N
4 0 3 0 0 0 0 2 2 0 0 0 1 0

输出样例:
在这里给出相应的输出。例如:

A M B C G H N D E F I L J K

#include <stdio.h>
#include<malloc.h>
#include<string.h>
int x[100100][2];
char y[100100][10];
int z[100100];
int t[100100];
int main()
{
    int n, a, b=1, c, d=0;
    char ch;
    scanf("%d", &n);
    for (a = 0; a < n; a++)
    {
        scanf("%s", y[a]);
    }
    for (a = 0; a < n; a++)
    {
        scanf("%d", &z[a]);
    }
    for (a = 0; a < n; a++)
    {
        x[b][0] = a;
        x[b][1] = z[a];
        t[a] = b;
        x[b - 1][1]--;
        for (; x[b][1] == 0;)
        {
            b--;
        }
        b++;
    }
    for (a = 1; a < 100; a++)
    {
        for (b = 0; b < n; b++)
        {
            if (t[b] == a)
            {
                if (d == 0)
                {
                    printf("%s", y[b]);
                    d = 1;
                }
                else
                printf(" %s", y[b]);
            }
        }
    }
    return 0;
}

数列查询
分数 100
作者 谷方明
单位 吉林大学
已知数列的通项公式为:

     f(n) = f(n-1)*11/10,f[1]=10. 
通项从左向右计算,*和/分别表示整数乘法和除法。
现在,要多次查询数列项的值。

输入格式:
第1行,1个整数q,表示查询的次数, 1≤q≤10000.
第2至q+1行,每行1个整数i,表示要查询f(i)的值。

输出格式:
q行,每行1个整数,表示f(i)的值。查询的值都在32位整数范围内。

输入样例:
在这里给出一组输入。例如:

3
1
2
3

输出样例:
在这里给出相应的输出。例如:

10
11
12

#include <stdio.h>
int x[10000100];
int y[10010];
int main()
{
    int n, a,i=0;
    x[1]=10;
    scanf("%d", &n);
    for (a = 0; a < n; a++)
    {
        scanf("%d", &y[a]);
        if (y[a] > i)
            i = y[a];
    }
    for (a = 1; a <= i; a++)
    {
        x[a + 1] = x[a] * 11 / 10;
    }
    for (a = 0; a < n-1; a++)
    {
        printf("%d\n", x[y[a]]);
    }
    printf("%d", x[y[a]]);
    return 0;
}

一篇文章由n个汉字构成,汉字从前到后依次编号为1,2,……,n。
有四种操作:

A i j表示把编号为i的汉字移动编号为j的汉字之前;

B i j表示把编号为i的汉字移动编号为j的汉字之后;

Q 0 i为询问编号为i的汉字之前的汉字的编号;

Q 1 i为询问编号为i的汉字之后的汉字的编号。

规定:1号汉字之前是n号汉字,n号汉字之后是1号汉字。

输入格式:
第1行,1个整数T,表示有T组测试数据, 1≤T≤9999.

随后的每一组测试数据中,第1行两个整数n和m,用空格分隔,分别代表汉字数和操作数,2≤n≤9999,1≤m≤9999;第2至m+1行,每行包含3个常量s、i和j,用空格分隔,s代表操作的类型,若s为A或B,则i和j表示汉字的编号,若s为Q,i代表0或1,j代表汉字的编号。

输出格式:
若干行,每行1个整数,对应每个询问的结果汉字编号。

输入样例:
在这里给出一组输入。例如:


9999 4 
B 1 2  
A 3 9999
Q 1 1
Q 0 3

输出样例:
在这里给出相应的输出。例如:

4
9998


#include<string.h>
#include<stdio.h>
#include <malloc.h>
struct cell
{
    int date;
    struct cell* next;
};
struct cell* head;
void fi(int b, int c)
{
    int a;
    struct cell* p,*p0;
    p0 = head;
    p = (struct cell*)malloc(sizeof(struct cell));
    p->date = c;
    for (a = 1; a < b; a++)
    {
        if (p0 == NULL)
            return;
        p0 = p0->next;
    }
    if (p0 == NULL)
        return;
    p->next = p0->next;
    p0->next = p;
}
void fe(int b)
{
    int a;
    struct cell* p=head,*p0;
    for (a = 1; a < b; a++)
    {
        if (p == NULL)
            return;
        p = p->next;
    }
    if (p->next == NULL||p==NULL)
        return;
    p0 = p->next->next;
    p->next =p0;
}
void fu(int b,int c)
{
    int a;
    struct cell* p = head;
    for (a = 0; a < b; a++)
    {
        if (p == NULL)
            return;
        p = p->next;
    }
    if (p == NULL)
        return;
    p->date = c;
}
int fq(int b)
{
    int a;
    struct cell* p = head;
    for (a = 0; a < b; a++)
    {
        if (p == NULL)
            return -1;
        p = p->next;
    }
    if (p == NULL)
        return -1;
    return p->date;
}
int main()
{
    head = (struct cell*)malloc(sizeof(struct cell));
    head->next = NULL;
    head->date = -1;
    int n, a, b, c,d;
    char ch;
    scanf("%d", &n);
    for (a = 0; a < n; a++)
    {
        scanf("%c", &ch);
        while (ch != 'I' && ch != 'E' && ch != 'U' && ch != 'Q')
            scanf("%c", &ch);
        if (ch == 'I')
        {
            scanf("%d %d", &b, &c);
            fi(b, c);
        }
        if (ch == 'E')
        {
            scanf("%d",&b);
            fe(b);
        }
        if (ch == 'U')
        {
            scanf("%d %d", &b, &c);
            fu(b, c);
        }
        if (ch == 'Q')
        {
            scanf("%d", &b);
            printf("%d\n",fq(b));
        }
    }
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值