Given an array, you are asked to perform a number of queries and divide the array into what are called, beautifulsubsequences.
The array has length . A function is defined to be a minimal possible , such that it's possible to divide array into beautiful subsequences. Note that each element of an array should belong to exactly one subsequence, and subsequence does not necessarily need to be consecutive.
A subsequence with length is called beautiful if and only if:
- or
- Let be a sorted version of . It must hold that for every
For instance, if , would be . Because, you can divide into beautiful subsequences either like and or like and .
You have to answer queries. Each query is of the type:
- : you need to change a value of to , i.e. . Here is .
After each query, for the value of , lets denote that value as , where indicates the query.
You need to find modulo .
Input Format
The first line contains a single integer , representing the length of array .
The next line contains the array given as space-separated integers.
The next line contains a single integer , representing the number of queries.
Each of the lines contain two integers and , which is described above.
Constraints
Output Format
Print the required answer in one line.
Sample Input 0
5
2 2 1 1 1
2
3 2
5 5
Sample Output 0
11
Explanation 0
The initial array is
- After query the array becomes this can be divided into subsequences as , and .
- After query the array becomes this can be divided into subsequences as , , and .
Hence, calculating we get
Sample Input 1
2
3 3
3
2 4
1 5
2 2
Sample Output 1
9
Explanation 1
The initial array is
- After query the array becomes this can be divided into subsequence as .
- After query the array becomes this can be divided into subsequence as .
- After query the array becomes this can be divided into subsequences as and .
Hence, calculating we get
题意:
每次操作变动一个数字。问你这些数字最少分成几个完美数列。
完美数列: 只有一个数字 或者 数字可以重新排列成连续的。
POINT:
用map记录下每个数字的出现次数。
用单调栈的思想来计算答案。
值为x。那么他对答案的贡献是num[x-1]-num[x]。负数则不计。
每次改变的时候只要部分比较就行了。不需要全部重新计算。
#include <iostream>
#include <stdio.h>
#include <cmath>
#include <string.h>
#include <map>
#include <algorithm>
using namespace std;
typedef long long LL;
const LL maxn = 1e6+6;
const LL inf = 0x3f3f3f3f;
const LL mod = 1e9+7;
map<int,int>mp;
map<int,int>temp;
int f(int x)//从left-right
{
int left=max(x-2,1);
int right=x+3;
int num=0;
for(int i=left+1;i<=right;i++){
if(mp[i]<mp[i-1])
num+=mp[i-1]-mp[i];
}
return num+mp[right];
}
int a[maxn];
int ans;
int ff(int x)//三个
{
if(x==1){
return max(mp[x],mp[x+1]);
}
int left=mp[x-1],now=mp[x],right=mp[x+1];
if(now<left&&now<right){
return now+left-now+right-now;
}
return max(max(now,right),left);
}
int main()
{
int n;
scanf("%d",&n);
int b[maxn];
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
b[i]=a[i];
mp[a[i]]++;
temp[a[i]]++;
}
sort(b+1,b+1+n);
int cnt=unique(b+1,b+1+n)-b-1;
for(int i=1;i<=cnt;i++){
if(mp[b[i]+1]==0){
ans+=mp[b[i]];//后面是0。则全要//因为b[i]的值不连续,重点!
}
if(mp[b[i]]<mp[b[i]-1]){
ans+=mp[b[i]-1]-mp[b[i]];
}
}
int q;
scanf("%d",&q);
LL aans=0;
for(int i=1;i<=q;i++){
int pos,val;
scanf("%d%d",&pos,&val);
if(a[pos]==val){
}else if(abs(a[pos]-val)>2){
int pre = ff(a[pos])+ff(val);
mp[a[pos]]--;
mp[val]++;
int now = ff(a[pos])+ff(val);
(ans+=now-pre+mod)%=mod;
}else{
int pre = f((a[pos]+val)/2);
mp[a[pos]]--;
mp[val]++;
int now = f((a[pos]+val)/2);
(ans+=now-pre+mod)%=mod;
}
a[pos]=val;
(aans+=(LL)ans*i%mod)%=mod;
}
printf("%lld\n",aans);
}