ACM详解(5)——排序

有些ACM 题需要使用一些基本的数据结构,下面首先介绍与排序相关的内容。
1、基本排序
Problem Description
These days, I am thinking about a question, how can I get a problem as easy as A+B? It is fairly difficulty to do such a thing. Of course, I got it after many waking nights.
Give you some integers, your task is to sort these number ascending ( 升序).
You should know how easy the problem is now!
Good luck!
Input
Input contains multiple test cases. The first line of the input is a single integer T which is the number of test cases. T test cases follow. Each test case contains an integer N (1<=N<=1000 the number of integers to be sorted) and then N integers follow in the same line.
It is guarantied that all integers are in the range of 32-int.
Output
For each case, print the sorting result, and one line one case.
Sample Input
2
3 2 1 3
9 1 4 7 2 5 8 3 6 9
Sample Output
1 2 3
1 2 3 4 5 6 7 8 9
翻译:对给定的数字序列进行排序。使用数据结构的基本排序算法即可。可以使用各种排序算法实现。另外在Java 中提供了排序方法,可以使用Arrays.sort 方法,参考下面的代码:
Arrays.sort(a);
其中a 是需要排序的数组。
下面给出了冒泡排序的代码供参考:
/*
* 冒泡排序
*/
public static int[] sort(int[] a){
// Arrays.sort(a);
for(int i=0;i<a.length-1;i++){
for(int j=a.length-1;j>i;j--){
if(a[j]<a[j-1]){
int temp = a[j];
a[j] = a[j-1];
a[j-1] = temp;
}
}
}
return a;
}
2、DNA Sorting
Description
One measure of ``unsortedness'' in a sequence is the number of pairs of entries that are out of order with respect to each other. For instance, in the letter sequence ``DAABEC'', this measure is 5, since D is greater than four letters to its right and E is greater than one letter to its right. This measure is called the number of inversions in the sequence. The sequence ``AACEDGG'' has only one inversion (E and D)---it is nearly sorted---while the sequence ``ZWQM'' has 6 inversions (it is as unsorted as can be---exactly the reverse of sorted).
You are responsible for cataloguing a sequence of DNA strings (sequences containing only the four letters A, C, G, and T). However, you want to catalog them, not in alphabetical order, but rather in order of ``sortedness'', from ``most sorted'' to ``least sorted''. All the strings are of the same length.
Input
The first line contains two integers: a positive integer n (0 < n <= 50) giving the length of the strings; and a positive integer m (0 < m <= 100) giving the number of strings. These are followed by m lines, each containing a string of length n.
Output
Output the list of input strings, arranged from ``most sorted'' to ``least sorted''. Since two strings can be equally sorted, then output them according to the orginal order.
Sample Input
10 6
AACATGAAGG
TTTTGGCCAA
TTTGGCCAAA
GATCAGATTT
CCCGGGGGGA
ATCGATGCAT
Sample Output
CCCGGGGGGA
AACATGAAGG
GATCAGATTT
ATCGATGCAT
TTTTGGCCAA
TTTGGCCAAA
翻译:对于一个序列的无序性可以使用相互之间无序的元素组的个数表示,例如字母序列DAABEC 的无序性是5,D大于后面的AABC,E大于后面的C。而AACEDGG 的无序性是1,因为只有E和D之间的顺序是乱的。
题目要求:对于给定的多个字符串(长度相同,由A, C, G 和T 组成),从最有序到最无序进行排列。
解题思路:计算每个字符串的无序性,然后进行排序即可。参考下面的代码:
/*
* DNA sorting
*/
public static void test3(String[] dnas){
Map invertions = new HashMap();
// 计算每个字符串的乱序数量
for(int i=0;i<dnas.length;i++){
invertions.put(dnas[i], count(dnas[i]));
}
// 排序
for(int i=0;i<dnas.length-1;i++){
for(int j=dnas.length-1;j>i;j--){
if((Integer)(invertions.get(dnas[j]))<(Integer)(invertions.get(dnas[j-1]))){
String temp = dnas[j];
dnas[j] = dnas[j-1];
dnas[j-1] = temp;
}
}
}
// 输出
for(String temp:dnas){
System.out.println(temp+invertions.get(temp));
}
}
// 计算无序性
public static int count(String dna){
int sum=0;
for(int i=0;i<dna.length()-1;i++){
char temp = dna.charAt(i);
for(int j=i+1;j<dna.length();j++){
if(temp>dna.charAt(j))
sum++;
}
}
return sum;
}
上面计算无序性的代码是通过遍历字符串中的每个元素,然后判断后续的每个字符和它之间是否有序,需要遍历两次。如果字符串不是很长,这种算法还可以接受。如果字符串很长,计算将很耗时。下面的方法进行了改进。
/*
* 计算无序性(改进算法)
*/
public static int count2(String dna){
int count[] = new int [4];
Arrays.fill(count,0);
int sum=0;
for ( int i=dna.length()-1;i>=0;i--){
char temp = dna.charAt(i);
switch (temp){
case 'A' :
count[0]++;
break ;
case 'C' :
count[1]++;
sum = sum+count[0]; // 加上 C 后面的 A 的个数
break ;
case 'G' :
count[2]++;
sum = sum+count[0]+count[1]; // 加上 G 后面的 AC 的数量
break ;
case 'T' :
count[3]++;
sum = sum+count[0]+count[1]+count[2]; // 加上 G 后面的 ACG 的数量
break ;
}
}
return sum;
}
另外在代码中,对序列进行排序是自己编写的排序算法。也可以使用系统提供的排序功能,需要编写一个类,参考代码如下:
class DNA implements Comparable{
String content;
int unsortness;
DNA(String content,int unsortness){
this.content = content;
this.unsortness = unsortness;
}
@Override
public int compareTo(Object o) {
return unsortness-((DNA)o).unsortness;
}
}
修改后的代码如下:
/*
* DNA sorting
*/
public static void test3(String[] dnas){
DNA newDnas[] = new DNA[dnas. length ];
for ( int i=0;i<dnas. length ;i++){
newDnas[i] = new DNA(dnas[i],count(dnas[i]));
}
Arrays.sort(newDnas); // 替换了原来的排序算法
// 输出
for (DNA temp:newDnas){
System. out .println(temp. content +temp. unsortness );
}
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值