注: 本文只是记录 ,您将从上面学习不到任何知识,除了 代码
(废话)第一次接触到树状数组,感觉接触到了新世界,理解这个思想用了好长时间,终于弄明白了(似懂非懂)。
还有接触到了 离散化的思想, 逆序数 , 感觉数学这么有用
时间限制: 1 Sec 内存限制: 32 MB
提交: 157 解决: 47
现在给你一个由n个互不相同的整数组成的序列,现在要求你任意交换相邻的两个数字,使序列成为升序序列,请问最少的交换次数是多少?
输入包含多组测试数据。每组输入第一行是一个正整数n(n<500000),表示序列的长度,当n=0时。 接下来的n行,每行一个整数a[i](0<=a[i]<=999999999),表示序列中第i个元素。
对于每组输入,输出使得所给序列升序的最少交换次数。
5
9
1
0
5
4
3
1
2
3
0
6
0
import java.util.Arrays;
import java.util.Scanner;
/**
* 树状数组
* @author Administrator
*
*/
class Node implements Comparable<Node>{
public int index;
public int value;
public Node(int index,int value){
this.index = index;
this.value = value;
}
@Override
public int compareTo(Node n) {
return this.value-n.value;
}
}
public class TreeArrayDemo {
private static int [] c ;
private static int [] array = new int [500010];
private static int maxn;
private static Node [] nodes ;
public static int lowbit(int x){
return x&(-x);
}
public static int getSum(int x)
{
int sum = 0 ;
for(int i = x;i>0;i-=lowbit(i)){
sum+=c[i];
}
return sum;
}
public static void update(int x,int val)
{
for(int i = x;i<=maxn;i+=lowbit(i)){
c[i]+=val;
}
}
public static void main(String[] args) {
Scanner cin = new Scanner(System.in);
while (cin.hasNext()) {
maxn = cin.nextInt();
if(maxn == 0)
{
break;
}
nodes = new Node [500010];
c = new int [500010];
for(int i = 1;i<=maxn;i++){
int index = i;
int val = cin.nextInt();
Node node = new Node(index, val);
nodes[i] = node;
}
//给节点进行排序
Arrays.sort(nodes, 1,maxn+1);
//对数据进行离散化
for(int i = 1;i<=maxn;i++){
array[nodes[i].index] = i;
}
for(int i = 1;i<=maxn;i++){
System.out.println(array[i]);
}
long answer = 0;
for(int i = 1;i<=maxn;i++)
{
update(array[i], 1);
int n = getSum(array[i]);
answer+=i-n;
}
System.out.println(answer);
}
}
}