给逆序对数求原数组
Posted Keep--Silent
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了给逆序对数求原数组相关的知识,希望对你有一定的参考价值。
文章目录
给正序对数求原数组
假设 正序对数是
0
1
2
1
2
0\\; 1 \\;2\\; 1\\; 2
01212
解决:
- 先管正序对数小的,从小往大放
- 正序对数相同时,从右往左放
0
0
0
0
0
0 \\; 0 \\; 0\\; 0 \\; 0
00000
1
0
0
0
0
1\\; 0\\; 0\\; 0 \\; 0
10000
1
3
0
2
0
1\\; 3\\; 0 \\; 2\\; 0
13020
1
3
5
2
4
1\\; 3 \\; 5 \\; 2 \\; 4
13524
例题
这题需要根据残缺的数组,补齐原数组
#include<bits/stdc++.h>
#include<cstring>
#include<string>
using namespace std;
typedef long long ll;
#define SIZE (1000000+10)
int a[SIZE];
int b[SIZE];
int flag[SIZE];
vector<int>pot[SIZE];
int main()
int i,j,n,k,p,x;
scanf("%d%d",&n,&k);
for(i=0;i<k;i++)
scanf("%d%d",&p,&x);
b[p]=x;
int maxn=0;
for(i=1;i<=n;i++)
if(b[i]==0)b[i]=b[i-1]+1;
else
if(b[i]>maxn+1)
cout<<-1<<endl;
return 0;
maxn=max(maxn,b[i]);
pot[b[i]].push_back(i);
int ans=1;
for(i=1;i<=n;i++)
for(j=pot[i].size()-1;j>=0;j--)
a[pot[i][j]]=ans++;
//for(i=1;i<=n;i++)printf("%d ",b[i]);cout<<endl;
for(i=1;i<=n;i++)printf("%d ",a[i]);cout<<endl;
return 0;
给逆序对数求原数组(原数各不相同
排序
本题关键是得到原数组
- 放入 0 0 1 2 . . . x − 1 x x + 1 . . . n − 2 0\\;0 \\;1 \\;2\\; ...\\;\\;x-1\\; x \\;x+1\\;... n-2 0012...x−1xx+1...n−2
- 多余的数从第二个位置开始加 ,可以得到逆序对数 0 1 2 . . . x x x + 1... n − 2 0\\; 1 \\;2 \\;...x\\; x\\; x+1... \\;n-2 012...xxx+1...n−2
- 然后再用当前位置扣去数字,可以得到正序对数 0 0 1 1 . . . 1 0 . . . 0 0\\; 0\\; 1 \\;1\\; ... \\;1\\; 0 \\;... \\;0 \\; 0011...10...0
- 先放0 ,再放1,从右往左放
#include<bits/stdc++.h>
using namespace std;
const int Size = 1e5 + 10;
#define ll long long
#define debug(x) cout<<#x<<" = "<<x<<" ";
#define debug1(a) debug(a);cout<<endl;
#define debug2(a,b) debug(a);debug1(b);
#define debug3(a,b,c) debug(a);debug2(b,c);
#define debugvec(x,n) cout<<#x<<": ";for(int asd=0;asd<n;asd++)cout<<x[asd]<<" ";cout<<endl;
#define debugvector(x) cout<<#x<<": ";for(int asd=0;asd<x.size();asd++)cout<<x[asd]<<" ";cout<<endl;
#define debugvectorstring(x) cout<<#x<<": ";for (auto& s : x) printf("%s", s.c_str());;cout<<endl;
int n, k = 100;
string s, ans;
vector<int>v;
void ini()
int i, t;
n = 1;
while (n * (n - 1) / 2 < k) n++;
v.push_back(0);
for (i = 0; i < n - 1; i++)v.push_back(i);
t = k - (n - 2) * (n - 1) / 2;
//debug3(k, (n - 2) * (n - 1) / 2, t);
for (i = n - 1; t; t--, i--)v[i]++;
for (i = 0; i < n; i++)v[i] = i - v[i];
//debugvec(v, n);
void sovle()
int i;
char ch = 'a';
s.resize(n);
for (i = n - 1; i >= 0; i--)if (!v[i]) s[i] = ch++;
for (i = n - 1; i >= 0; i--)if (v[i]) s[i] = ch++;
cout << s << endl;
int main()
//freopen("C:\\\\Users\\\\31531\\\\Desktop\\\\input.txt", "r", stdin);
ini();
sovle();
return 0;
给逆序对数求原数组(原数可相同
当 k ≤ 26 ( 26 − 1 ) 2 = 325 时 k \\leq \\cfrac26(26-1)2=325时 k≤226(26−1)=325时
- 放入 0 0 1 2 . . . x − 1 x x + 1 . . . n − 2 0\\;0 \\;1 \\;2\\; ...\\;\\;x-1\\; x \\;x+1\\;... n-2 0012...x−1xx+1...n−2
- 从倒二位开始 v [ i ] + + v[i]++ v[i]++,每次往前挪两格 i − = 2 i-=2 i−=2
- 从正二位或者正三位开始 v [ i ] + + v[i]++ v[i]++,每次往后挪两格 i + = 2 i+=2 i+=2
- 已经是递增的顺序了,直接从右往左放
#include<bits/stdc++.h>
using namespace std;
const int Size = 3e3 + 10;
#define ll long long
#define debug(x) cout<<#x<<" = "<<x<<" ";
#define debug1(a) debug(a);cout<<endl;
#define debug2(a,b) debug(a);debug1(b);
#define debug3(a,b,c) debug(a);debug2(b,c);
#define debugvec(x,n) cout<<#x<<": ";for(int asd=0;asd<n;asd++)cout<<x[asd]<<" ";cout<<endl;
#define debugvector(x) cout<<#x<<": ";for(int asd=0;asd<x.size();asd++)cout<<x[asd]<<" ";cout<<endl;
#define debugvectorstring(x) cout<<#x<<": ";for (auto& s : x) printf("%s", s.c_str());;cout<<endl;
string s = "";
int n,k=100;
vector<int>v;
void debugs(string s)
for (auto ch : s)
printf("%3c", ch);
cout << endl;
int p[2] = 0,0 ;
for (int i = 0; i < s.size(); i++)
int cnt = 0;
for (int j = i - 1; j >= 0; j--)
if (s[j] > s[i])
cnt++;
p[1] += cnt;
printf("%3d", cnt);
cout << endl;
//debug2(p[0], p[1]);
void ini()
int i, t;
n = 1;
while (n * (n - 1) / 2 < k) n++;
t = k - (n - 1) * (n - 2) / 2;
v.push_back(0);
for (i = 0; i < n - 1; i++)v.push_back(i);
//debugvec(v, n);
for (i = n - 2; i > 0 && t; i-=2, t--)v[i]++;
//debugvec(v, n);
for (i = 1 + (n % 2); t; t--, i += 2)v[i]++;
//debugvec(v, n);
void solve()
s.resize(n);
char ch = 'a';
s[n - 1] = ch;
for (int i = n 以上是关于给逆序对数求原数组的主要内容,如果未能解决你的问题,请参考以下文章
归并排序(归并排序求逆序对数)--16--归并排序--Leetcode面试题51.数组中的逆序对