/[projects]/dao/DaoAdresseService/src/main/java/dk/daoas/daoadresseservice/util/NaturalOrderComparator.java
ViewVC logotype

Contents of /dao/DaoAdresseService/src/main/java/dk/daoas/daoadresseservice/util/NaturalOrderComparator.java

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2537 - (show annotations) (download)
Mon May 11 07:57:19 2015 UTC (9 years ago) by torben
File size: 5508 byte(s)
Silence warnings
1 package dk.daoas.daoadresseservice.util;
2
3 import java.io.Serializable;
4
5 import java.util.Arrays;
6 import java.util.Collections;
7 import java.util.Comparator;
8 import java.util.List;
9
10 /*
11 NaturalOrderComparator.java -- Perform 'natural order' comparisons of strings in Java.
12 Copyright (C) 2003 by Pierre-Luc Paour <natorder@paour.com>
13
14 Based on the C version by Martin Pool, of which this is more or less a straight conversion.
15 Copyright (C) 2000 by Martin Pool <mbp@humbug.org.au>
16
17 This software is provided 'as-is', without any express or implied
18 warranty. In no event will the authors be held liable for any damages
19 arising from the use of this software.
20
21 Permission is granted to anyone to use this software for any purpose,
22 including commercial applications, and to alter it and redistribute it
23 freely, subject to the following restrictions:
24
25 1. The origin of this software must not be misrepresented; you must not
26 claim that you wrote the original software. If you use this software
27 in a product, an acknowledgment in the product documentation would be
28 appreciated but is not required.
29 2. Altered source versions must be plainly marked as such, and must not be
30 misrepresented as being the original software.
31 3. This notice may not be removed or altered from any source distribution.
32 */
33
34
35
36 public class NaturalOrderComparator<T> implements Comparator<T>, Serializable
37 {
38 private static final long serialVersionUID = 1L;
39
40 int compareRight(String a, String b)
41 {
42 int bias = 0;
43 int ia = 0;
44 int ib = 0;
45
46 // The longest run of digits wins. That aside, the greatest
47 // value wins, but we can't know that it will until we've scanned
48 // both numbers to know that they have the same magnitude, so we
49 // remember it in BIAS.
50 for (;; ia++, ib++)
51 {
52 char ca = charAt(a, ia);
53 char cb = charAt(b, ib);
54
55 if (!Character.isDigit(ca) && !Character.isDigit(cb))
56 {
57 return bias;
58 }
59 else if (!Character.isDigit(ca))
60 {
61 return -1;
62 }
63 else if (!Character.isDigit(cb))
64 {
65 return +1;
66 }
67 else if (ca < cb)
68 {
69 if (bias == 0)
70 {
71 bias = -1;
72 }
73 }
74 else if (ca > cb)
75 {
76 if (bias == 0)
77 bias = +1;
78 }
79 else if (ca == 0 && cb == 0)
80 {
81 return bias;
82 }
83 }
84 }
85
86 public int compare(T o1, T o2)
87 {
88 String a = o1.toString();
89 String b = o2.toString();
90
91 int ia = 0, ib = 0;
92 int nza = 0, nzb = 0;
93 char ca, cb;
94 int result;
95
96 while (true)
97 {
98 // only count the number of zeroes leading the last number compared
99 nza = nzb = 0;
100
101 ca = charAt(a, ia);
102 cb = charAt(b, ib);
103
104 // skip over leading spaces or zeros
105 while (Character.isSpaceChar(ca) || ca == '0')
106 {
107 if (ca == '0')
108 {
109 nza++;
110 }
111 else
112 {
113 // only count consecutive zeroes
114 nza = 0;
115 }
116
117 ca = charAt(a, ++ia);
118 }
119
120 while (Character.isSpaceChar(cb) || cb == '0')
121 {
122 if (cb == '0')
123 {
124 nzb++;
125 }
126 else
127 {
128 // only count consecutive zeroes
129 nzb = 0;
130 }
131
132 cb = charAt(b, ++ib);
133 }
134
135 // process run of digits
136 if (Character.isDigit(ca) && Character.isDigit(cb))
137 {
138 if ((result = compareRight(a.substring(ia), b.substring(ib))) != 0)
139 {
140 return result;
141 }
142 }
143
144 if (ca == 0 && cb == 0)
145 {
146 // The strings compare the same. Perhaps the caller
147 // will want to call strcmp to break the tie.
148 return nza - nzb;
149 }
150
151 if (ca < cb)
152 {
153 return -1;
154 }
155 else if (ca > cb)
156 {
157 return +1;
158 }
159
160 ++ia;
161 ++ib;
162 }
163 }
164
165 static char charAt(String s, int i)
166 {
167 if (i >= s.length())
168 {
169 return 0;
170 }
171 else
172 {
173 return s.charAt(i);
174 }
175 }
176
177 public static void main(String[] args)
178 {
179 String[] strings = new String[] { "1-2", "1-02", "1-20", "10-20", "fred", "jane", "pic01",
180 "pic2", "pic02", "pic02a", "pic3", "pic4", "pic 4 else", "pic 5", "pic05", "pic 5",
181 "pic 5 something", "pic 6", "pic 7", "pic100", "pic100a", "pic120", "pic121",
182 "pic02000", "tom", "x2-g8", "x2-y7", "x2-y08", "x8-y8" };
183
184 List<String> orig = Arrays.asList(strings);
185
186 System.out.println("Original: " + orig);
187
188 List<String> scrambled = Arrays.asList(strings);
189 Collections.shuffle(scrambled);
190
191 System.out.println("Scrambled: " + scrambled);
192
193 Collections.sort(scrambled, new NaturalOrderComparator<String>());
194
195 System.out.println("Sorted: " + scrambled);
196 }
197 }

  ViewVC Help
Powered by ViewVC 1.1.20