cf 830B - Cards Sorting 树状数组

B. Cards Sorting

time limit per test

1 second

memory limit per test

256 megabytes

input

standard input

output

standard output

Vasily has a deck of cards consisting of n cards. There is an integer on each of the cards, this integer is between 1 and 100 000, inclusive. It is possible that some cards have the same integers on them.

Vasily decided to sort the cards. To do this, he repeatedly takes the top card from the deck, and if the number on it equals the minimum number written on the cards in the deck, then he places the card away. Otherwise, he puts it under the deck and takes the next card from the top, and so on. The process ends as soon as there are no cards in the deck. You can assume that Vasily always knows the minimum number written on some card in the remaining deck, but doesn‘t know where this card (or these cards) is.

You are to determine the total number of times Vasily takes the top card from the deck.

Input

The first line contains single integer n (1 ≤ n ≤ 100 000) — the number of cards in the deck.

The second line contains a sequence of n integers a1, a2, ..., an (1 ≤ ai ≤ 100 000), where ai is the number written on the i-th from top card in the deck.

Output

Print the total number of times Vasily takes the top card from the deck.

Examples

input

46 3 1 2

output

7

input

11000

output

1

input

73 3 3 3 3 3 3

output

7

Note

In the first example Vasily at first looks at the card with number 6 on it, puts it under the deck, then on the card with number 3, puts it under the deck, and then on the card with number 1. He places away the card with 1, because the number written on it is the minimum among the remaining cards. After that the cards from top to bottom are [2, 6, 3]. Then Vasily looks at the top card with number 2 and puts it away. After that the cards from top to bottom are [6, 3]. Then Vasily looks at card 6, puts it under the deck, then at card 3 and puts it away. Then there is only one card with number 6 on it, and Vasily looks at it and puts it away. Thus, in total Vasily looks at 7 cards.

题意:

有n标有数字的张牌,摞在桌子上,现在想要给牌排序排序方法是:每次抽出最上面的牌,如果他是剩余的这摞牌中最小的就把他拿出来,否则把他放到最下面。问拿完所有的牌的总次数是多少。

代码:

//可以看出每次都是O(n)一遍扔掉最小的(可能有多个相同的或不同的)之后剩余的牌变换次数+1(剩余的相对位置保持不变),直到没有牌为止,这是O(nn)的。
//可以用树状数组记录每个位置区间段中有多少张牌,当前扔掉的最小的牌的位置是递增的时(即在上一个被扔掉的牌的位置的右边)
//那么次数+1的牌就只有当前最小牌与上个被扔掉的牌的位置之间的牌,否则就是这个区间以外的区间的牌的次数+1,然后扔掉的牌
//从树状数组中去掉。O(nlogn)
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn=100000;
int A[maxn*4+10],n;
vector<int>v[maxn*4];
void update(int id,int v)
{
    while(id<=maxn*4){
        A[id]+=v;
        id+=(id&(-id));
    }
}
int query(int id)
{
    int sum=0;
    while(id){
        sum+=A[id];
        id-=(id&(-id));
    }
    return sum;
}
int main()
{
    scanf("%d",&n);
    memset(A,0,sizeof(A));
    for(int i=1;i<=n;i++){
        int x;
        scanf("%d",&x);
        v[x].push_back(i);
        update(i,1);
    }
    int last=0;
    ll ans=0;
    for(int i=1;i<=maxn;i++){
        int Size=v[i].size(),tmp=-1;
        if(Size==0) continue;
        for(int j=0;j<Size;j++){
            if(v[i][j]<last)
                tmp=v[i][j];
        }
        if(tmp==-1){
            ans+=query(v[i][Size-1])-query(last);
            last=v[i][Size-1];
        }
        else{
            ans+=query(maxn)-(query(last)-query(tmp));
            last=tmp;
        }
        for(int j=0;j<Size;j++)
            update(v[i][j],-1);
    }
    printf("%lld\n",ans);
    return 0;
}
时间: 2024-08-27 00:20:32

cf 830B - Cards Sorting 树状数组的相关文章

HDU Cow Sorting (树状数组)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2838 Cow Sorting Problem Description Sherlock's N (1 ≤ N ≤ 100,000) cows are lined up to be milked in the evening. Each cow has a unique "grumpiness" level in the range 1...100,000. Since grumpy cow

Codeforces Round #227 (Div. 2)---E. George and Cards(贪心, 树状数组+set维护, 好题!)

George is a cat, so he loves playing very much. Vitaly put n cards in a row in front of George. Each card has one integer written on it. All cards had distinct numbers written on them. Let's number the cards from the left to the right with integers f

CF 351D, 离线处理+树状数组/莫队算法

颓颓颓 题目大意:给你m个区间询问,询问区间内有多少个不相同的数以及存不存在一种数字组成的数列为等差间隔的数列. 解:离线询问,不相同的数其实是老做法了,但是巧妙的是数字是否为等差间隔.我们把询问按右区间排序,可知等差间隔必然是连续的一段,那么从当前枚举点往左,合法数列必然是连续的一段,那么我们用树状数组+1-1维护区间延伸到哪里,然后询问[l,i]当中和是否为零就知道有没有符合的连续一段等差间隔数列了. 顺便这题官解是莫队,正好我也去研究一下莫队吧,现在先贴一个离线nlogn的做法,递归学会莫

HDU - 2838 Cow Sorting (树状数组 + 逆序对)

HDU - 2838 Cow Sorting Time Limit: 1000MS   Memory Limit: 32768KB   64bit IO Format: %I64d & %I64u Submit Status Description Sherlock's N (1 ≤ N ≤ 100,000) cows are lined up to be milked in the evening. Each cow has a unique "grumpiness" lev

hdu 2838 Cow Sorting 树状数组求所有比x小的数的个数

Cow Sorting Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 4766    Accepted Submission(s): 1727 Problem Description Sherlock's N (1 ≤ N ≤ 100,000) cows are lined up to be milked in the evening.

CF 313 DIV2 B 树状数组

http://codeforces.com/contest/313/problem/B 题目大意 给一个区间,问你这个区间里面有几个连续相同的字符. 思路: 表示个人用树状数组来写的...了解了树状数组的本质就行了. 当然用sum[r]-sum[l]也是可以的

hdu2838Cow Sorting树状数组求逆序对

//对于数列中的一个数,在它前面比它大的一定要和它交换 //在它后面比它小的一定得和它交换 //可以用树状数组存入每一个数在它之前比它小的数的个数 //那么(i-1)-total[i]为在它前面比它大的数的个数 //然后在所有数都存入树状数组后用getsum(num[i])可以求出整个数列中比这个数小的数的个数 //那么getsum(num[i])-1-total[i]则为在它之后比它小的数的个数 //ans+=num[i]*(i-2+getsum(num[i])-2*total[i]); #i

hdu 2838 coew sorting(树状数组)

求逆序对的和 分析:其实这个结果和逆序数有关,对某个位置i,如果前面比他大的有x个,那么a[i]至少要加x次 如果后面有y个比a[i]小,那么a[i]至少要加y次,也就是说用两个树状数组来分别维护当前位置时前面有多少比他大,后面有多少个比他小 如求逆序数两两的总和: 如 3 2 1 :sum=(3+2)+(3+1)+(2+1)=12;   1 2 3: sum=0; 对于新插入的一个元素,运用树状数组,可以求得比它小的元素的个数,比它小的元素的和,在它之前的元素的总和. 而对于每一个新元素,其s

HDU5122 K.Bro Sorting 树状数组类逆序数应用

题意很简单,看案例就能懂,一个长度为n的序列,要重新排序,升序,每一次拿这个数跟后面所有数比较,需要移动尽可能往后面移动,问需要操作几次 对案例进行分析,从后往前面判,若发现前面有比当前这个数大的数答案就加1,但是发现后面很难讨论清楚,还得正向来分析,当前这个数,若后面有数字比它小,那就肯定需要操作一次的,由此想到了树状数组求逆序数中的一个操作,树状数组求逆序数就是需要先求出当前树状数组里面有多少个数比当前这个数小,于是想到了,把这个数组里的数字从后面往前面 一个一个加进树状数组里,每加一个,就