1 16 17 package de.schlichtherle.io.util; 18 19 import java.io.File ; 20 21 27 public class Paths { 28 29 33 public static final String normalize( 34 final String path) { 35 return normalize(path, File.separatorChar); 36 } 37 38 57 public static String normalize( 58 final String path, 59 final char separatorChar) { 60 final int prefixLen = prefixLength(path, separatorChar); 61 final int pathLen = path.length(); 62 final StringBuffer buffer = new StringBuffer (pathLen); 63 normalize(path.substring(prefixLen, pathLen), separatorChar, 0, pathLen - prefixLen, buffer); 64 buffer.insert(0, path.substring(0, prefixLen)); 65 if (buffer.length() == prefixLen 66 && (prefixLen <= 0 || buffer.charAt(prefixLen - 1) != separatorChar)) 67 buffer.append('.'); 68 if (pathLen > 0 && path.charAt(pathLen - 1) == separatorChar) 69 if (buffer.charAt(buffer.length() - 1) != separatorChar) 70 buffer.append(separatorChar); final String result = buffer.toString(); 72 return path.equals(result) ? path : result; 73 } 74 75 99 private static int normalize( 100 final String path, 101 final char separatorChar, 102 final int skip, 103 final int end, 104 final StringBuffer result) { 105 assert skip >= 0; 106 if (end <= 0) 107 return 0; 108 109 final int next = path.lastIndexOf(separatorChar, end - 1); 110 final String base = path.substring(next + 1, end); 111 final int skipped; 112 if (base.length() == 0 || ".".equals(base)) { 113 return normalize(path, separatorChar, skip, next, result); 114 } else if ("..".equals(base)) { 115 final int toSkip = skip + 1; 116 skipped = normalize(path, separatorChar, toSkip, next, result); 117 assert skipped <= toSkip; 118 if (skipped == toSkip) 119 return skip; 120 } else if (skip > 0) { 121 return normalize(path, separatorChar, skip - 1, next, result) + 1; 122 } else { 123 assert skip == 0; 124 skipped = normalize(path, separatorChar, skip, next, result); 125 assert skipped == 0; 126 } 127 128 final int resultLen = result.length(); 129 if (resultLen > 0 && result.charAt(resultLen - 1) != separatorChar) 130 result.append(separatorChar); 131 result.append(base); 132 return skipped; 133 } 134 135 146 public final static String cutTrailingSeparators( 147 final String path, 148 final char separatorChar) { 149 int i = path.length(); 150 if (i <= 0 || path.charAt(--i) != separatorChar) 151 return path; 152 while (i > 0 && path.charAt(--i) == separatorChar) 153 ; 154 return path.substring(0, ++i); 155 } 156 157 170 public final static String cutTrailingSeparator( 171 final String path, 172 final char separatorChar) { 173 final int pathEnd = path.length() - 1; 174 if (pathEnd > 0 && path.charAt(pathEnd) == separatorChar) 175 return path.substring(0, pathEnd); 176 else 177 return path; 178 } 179 180 184 public static final String [] split( 185 final String path) { 186 return split(path, File.separatorChar); 187 } 188 189 210 public static final String [] split( 211 final String path, 212 final char separatorChar) { 213 return split(path, separatorChar, new String [2]); 214 } 215 216 224 public static String [] split( 225 final String path, 226 final char separatorChar, 227 final String [] split) { 228 final int prefix = prefixLength(path, separatorChar); 229 230 int base = -1; 232 int end = path.length() - 1; 233 if (prefix <= end) { 234 end = lastIndexNot(path, separatorChar, end); 235 base = path.lastIndexOf(separatorChar, end); 236 if (base < prefix) 237 base = -1; 238 } 239 end++; 241 if (base != -1) { final int j = lastIndexNot(path, separatorChar, base) + 1; 244 split[0] = path.substring(0, j > prefix ? j : prefix); 245 split[1] = path.substring(base + 1, end); 246 } else { if (0 < prefix && prefix < end) split[0] = path.substring(0, prefix); else 250 split[0] = null; split[1] = path.substring(prefix, end); 252 } 253 254 return split; 255 } 256 257 275 private static int prefixLength(final String path, final char separatorChar) { 276 final int pathLen = path.length(); 277 int len = 0; if (pathLen > 0 && path.charAt(0) == separatorChar) { 279 len++; } else if (pathLen > 1 && path.charAt(1) == ':') { 281 final char drive = path.charAt(0); 282 if ('A' <= drive && drive <= 'Z' 283 || 'a' <= drive && drive <= 'z') { len = 2; 286 } 287 } 288 if (pathLen > len && path.charAt(len) == separatorChar) 289 len++; return len; 291 } 292 293 private static final int lastIndexNot(String path, char separatorChar, int last) { 294 while (path.charAt(last) == separatorChar && --last >= 0) 295 ; 296 return last; 297 } 298 299 300 protected Paths() { 301 } 302 } 303 | Popular Tags |