暑假训练第一期---思维题1

A - Little Robber Girl’s Zoo

CodeForces 686B

Time Limit:2000MS Memory Limit:262144KB 64bit IO Format:%I64d & %I64u

Description
Little Robber Girl likes to scare animals in her zoo for fun. She decided to arrange the animals in a row in the order of non-decreasing height. However, the animals were so scared that they couldn’t stay in the right places.

The robber girl was angry at first, but then she decided to arrange the animals herself. She repeatedly names numbers l and r such that r - l + 1 is even. After that animals that occupy positions between l and r inclusively are rearranged as follows: the animal at position l swaps places with the animal at position l + 1, the animal l + 2 swaps with the animal l + 3, …, finally, the animal at position r - 1 swaps with the animal r.

Help the robber girl to arrange the animals in the order of non-decreasing height. You should name at most 20 000 segments, since otherwise the robber girl will become bored and will start scaring the animals again.

Input
The first line contains a single integer n (1 ≤ n ≤ 100) — number of animals in the robber girl’s zoo.

The second line contains n space-separated integers a1, a2, …, an (1 ≤ ai ≤ 109), where ai is the height of the animal occupying the i-th place.

Output
Print the sequence of operations that will rearrange the animals by non-decreasing height.

The output should contain several lines, i-th of the lines should contain two space-separated integers li and ri (1 ≤ li < ri ≤ n) — descriptions of segments the robber girl should name. The segments should be described in the order the operations are performed.

The number of operations should not exceed 20 000.

If the animals are arranged correctly from the start, you are allowed to output nothing.

Sample Input
Input
4
2 1 4 3
Output
1 4
Input
7
36 28 57 39 66 69 68
Output
1 4
6 7
Input
5
1 2 1 2 1
Output
2 5
3 4
1 4
1 4

注意这是一道Special Judge的题目,也是第一次被这种题目坑。
它的意思是给你一组数,规模不超过100,在20000次交换内把这组数变为有序的;
然后输出每次交换的两个数的下标;
直接用冒泡排序写,然后将每次交换的 两个数输出来就可以了;
这里的判题不是唯一解,而是根据你的答案对输入值进行交换,看最后的结果是否是有序的;
这就是Special Judge的典型例子;

下面是关于Special Judge的定义:
http://acm.csu.edu.cn/OnlineJudge/problem.php?id=1344

代码如下:

#include 
#include 
using namespace std;
int a[110];
int main()
{
    int n;
    scanf("%d",&n);
    for(int i=1;i<=n;i++)
    {
        scanf("%d",&a[i]);
    }
    for(int i=0;ifor(int j=2;j<=n;j++)
        {   
            if(a[j-1]>a[j])
            {
                swap(a[j-1],a[j]);
                printf("%d %d\n",j-1,j);
            }
        }
    }
}


B - Alyona and Numbers

CodeForces 682A

Time Limit:1000MS Memory Limit:262144KB 64bit IO Format:%I64d & %I64u

Description
After finishing eating her bun, Alyona came up with two integers n and m. She decided to write down two columns of integers — the first column containing integers from 1 to n and the second containing integers from 1 to m. Now the girl wants to count how many pairs of integers she can choose, one from the first column and the other from the second column, such that their sum is divisible by 5.

Formally, Alyona wants to count the number of pairs of integers (x, y) such that 1 ≤ x ≤ n, 1 ≤ y ≤ m and equals 0.

As usual, Alyona has some troubles and asks you to help.

Input
The only line of the input contains two integers n and m (1 ≤ n, m ≤ 1 000 000).

Output
Print the only integer — the number of pairs of integers (x, y) such that 1 ≤ x ≤ n, 1 ≤ y ≤ m and (x + y) is divisible by 5.

Sample Input
Input
6 12
Output
14
Input
11 14
Output
31
Input
1 5
Output
1
Input
3 8
Output
5
Input
5 7
Output
7
Input
21 21
Output
88

这个题的意思是说有两个0—10^6范围内的数,计算各自范围内有多少加起来被5整除的数;
直接遍历是10^12超时严重,所以直接观察,1—5是一个循环,所以直接计算1—5的数,最后在算剩下的;

代码如下:

#include 
#include 
#include 
using namespace std;
typedef long long ll;
ll a[6]={0};
int main()
{
    int m,n;
    scanf("%d%d",&n,&m);
    if(n<=5||m<=5)
    {
        ll sum1=0;
        for(int i=1;i<=n;i++)
        {
            for(int j=1;j<=m;j++)
            {
                if((i+j)%5==0)
                    sum1++;
            }
        }
        printf("%I64d\n",sum1);
    }
    else
    {
        ll sum3=0,sum4=0;
        for(int i=1;i<=5;i++)
        {
            ll sum2=0;
            for(int j=1;j<=m;j++)
            {
                if((j+i)%5==0)
                {
                    sum2++;
                    sum4++;
                }
            }
            a[i]=sum2;
        }
        sum3=n/5*sum4;
        for(int i=1;i<=n%5;i++)
        {
            sum3+=a[i];

        }
        printf("%I64d\n",sum3);    //注意按要求使用%I64d;
    }
    return 0;
}


C - Alyona and Mex

CodeForces 682B

Time Limit:1000MS Memory Limit:262144KB 64bit IO Format:%I64d & %I64u

Description
Someone gave Alyona an array containing n positive integers a1, a2, …, an. In one operation, Alyona can choose any element of the array and decrease it, i.e. replace with any positive integer that is smaller than the current one. Alyona can repeat this operation as many times as she wants. In particular, she may not apply any operation to the array at all.

Formally, after applying some operations Alyona will get an array of n positive integers b1, b2, …, bn such that 1 ≤ bi ≤ ai for every 1 ≤ i ≤ n. Your task is to determine the maximum possible value of mex of this array.

Mex of an array in this problem is the minimum positive integer that doesn’t appear in this array. For example, mex of the array containing 1, 3 and 4 is equal to 2, while mex of the array containing 2, 3 and 2 is equal to 1.

Input
The first line of the input contains a single integer n (1 ≤ n ≤ 100 000) — the number of elements in the Alyona’s array.

The second line of the input contains n integers a1, a2, …, an (1 ≤ ai ≤ 109) — the elements of the array.

Output
Print one positive integer — the maximum possible value of mex of the array after Alyona applies some (possibly none) operations.

Sample Input
Input
5
1 3 3 3 6
Output
5
Input
2
2 1
Output
3

这个题目意思是指给你一组数,然后可以对这组数的每个元素进行操作,操作是可以减少这个数,最后求不能连续到达的最小的数,解题思路就是先对数组进行升序排序,再从0开始对ans与每个数进行判断,如果当前数比ans大,就将ans+1,如果小就跳过;
比如说5 5 5 5 5 经过操作后可以视为 1 2 3 4 5 那么结果就是6;

代码如下:

#include 
#include 
#include 
using namespace std;
int a[100010];
int main()
{
    int n;
    scanf("%d",&n);
    for(int i=0;iscanf("%d",&a[i]);
    }
    sort(a,a+n);
    int ans=0; 
    for(int i=0;iif(ansprintf("%d",ans+1);
    return 0;
}


D - Joty and Chocolate

CodeForces 678C

Time Limit:1000MS Memory Limit:262144KB 64bit IO Format:%I64d & %I64u

Description
Little Joty has got a task to do. She has a line of n tiles indexed from 1 to n. She has to paint them in a strange pattern.

An unpainted tile should be painted Red if it’s index is divisible by a and an unpainted tile should be painted Blue if it’s index is divisible by b. So the tile with the number divisible by a and b can be either painted Red or Blue.

After her painting is done, she will get p chocolates for each tile that is painted Red and q chocolates for each tile that is painted Blue.

Note that she can paint tiles in any order she wants.

Given the required information, find the maximum number of chocolates Joty can get.

Input
The only line contains five integers n, a, b, p and q (1 ≤ n, a, b, p, q ≤ 109).

Output
Print the only integer s — the maximum number of chocolates Joty can get.

Note that the answer can be too large, so you should use 64-bit integer type to store it. In C++ you can use the long long integer type and in Java you can use long integer type.

Sample Input
Input
5 2 3 12 15
Output
39
Input
20 2 3 3 5
Output
51

这个题目很简单,意思是有数n,如果 1—n 中有可以被a整除的数,那么这个数的价值就是 p,
同理如果有被b整除的数,就是q,如果同时被a和b整除的话就是p,q中最大的那个数,最后算可以得到的最大的价值。直接统计个数就行,同时被a,b整除的就是a,b的最小公倍数。

代码如下:

#include 
#include 
#include 
#include  
using namespace std;
typedef long long ll;           //注意全用long long
ll n,a,b,p,q;
ll gcd(ll a,ll b){return b==0?a:gcd(b,a%b);}
ll lcm(ll a,ll b){return a*b/gcd(a,b);}
int main()
{
    scanf("%lld%lld%lld%lld%lld",&n,&a,&b,&p,&q);
    ll ans;
    ll l1=n/a,l2=n/b,l3=n/lcm(a,b);
    ans=(l1-l3)*p+(l2-l3)*q+max(p,q)*l3;
    printf("%lld",ans);
    return 0;
}


E - Pyramid of Glasses

CodeForces 676B

Time Limit:1000MS Memory Limit:262144KB 64bit IO Format:%I64d & %I64u

Description
Mary has just graduated from one well-known University and is now attending celebration party. Students like to dream of a beautiful life, so they used champagne glasses to construct a small pyramid. The height of the pyramid is n. The top level consists of only 1 glass, that stands on 2 glasses on the second level (counting from the top), then 3 glasses on the third level and so on.The bottom level consists of n glasses.

Vlad has seen in the movies many times how the champagne beautifully flows from top levels to bottom ones, filling all the glasses simultaneously. So he took a bottle and started to pour it in the glass located at the top of the pyramid.

Each second, Vlad pours to the top glass the amount of champagne equal to the size of exactly one glass. If the glass is already full, but there is some champagne flowing in it, then it pours over the edge of the glass and is equally distributed over two glasses standing under. If the overflowed glass is at the bottom level, then the champagne pours on the table. For the purpose of this problem we consider that champagne is distributed among pyramid glasses immediately. Vlad is interested in the number of completely full glasses if he stops pouring champagne in t seconds.

Pictures below illustrate the pyramid consisting of three levels.


Input
The only line of the input contains two integers n and t (1 ≤ n ≤ 10, 0 ≤ t ≤ 10 000) — the height of the pyramid and the number of seconds Vlad will be pouring champagne from the bottle.

Output
Print the single integer — the number of completely full glasses after t seconds.

Sample Input
Input
3 5
Output
4
Input
4 8
Output
6

这个题很有趣,有呈金字塔形摆放的n层杯子,然后在最上面那个以每秒一杯的速度倒水,问你t秒后有多少杯子是满的;

我是这么想的,开一个二维数组a[15][15],用来表示t秒钟后流过每个杯子各自的总的水量,最后只需判断这些杯子里面有哪些是超过1的就是装满的。然后从第二层开始,每个杯子的水都是从上一层来的,即
a[i][j] = (a[i-1][j]-1) / 2 && a[i][j] = (a[i-1][j-1]-1) / 2;
这里 注意减1是要把留在杯子中的减掉,当然在计算这个之前分别判断两边杯子中的水是否都是满的即 >1;

代码如下:

#include 
#include 
#include 
using namespace std;
int ans=1;
double a[15][15]={0};
int main()
{
    int n,t;
    scanf("%d%d",&n,&t);
    a[1][1]=t;
    for(int i=2;i<=n;i++)
    {
        for(int j=1;j<=i;j++)
        {
            if(a[i-1][j-1]>1)
            {
                a[i][j]+=(a[i-1][j-1]-1)/2;
            }
            if(a[i-1][j]>1)
            {
                a[i][j]+=(a[i-1][j]-1)/2;
            }
            if(a[i][j]>=1)
            {
                ans++;
            }
        }
    }
    printf("%d",t==0?0:ans);
    return 0;
} 


仅代表个人观点,欢迎交流探讨;

暑假训练第一期---思维题1_第1张图片

图自P站 id=56066120

你可能感兴趣的:(暑假)