我目前在研究一个简单的编程问题,可能会很有趣,至少对于那些认为编程是艺术的人来说 :) 所以这是它:
如何最好地表示长整型为字符串,同时保持它们的自然顺序?
此外,字符串表示应该匹配^[A-Za-z0-9]+$
。(我不太严格,但请避免使用控制字符或任何可能导致编码困扰、在 XML 中非法、具有换行符或类似字符的内容,这些肯定会引起问题)
这是一个 JUnit 测试用例:
@Test
public void longConversion() {
final long[] longs = { Long.MIN_VALUE, Long.MAX_VALUE, -5664572164553633853L,
-8089688774612278460L, 7275969614015446693L, 6698053890185294393L,
734107703014507538L, -350843201400906614L, -4760869192643699168L,
-2113787362183747885L, -5933876587372268970L, -7214749093842310327L, };
// keep it reproducible
//Collections.shuffle(Arrays.asList(longs));
final String[] strings = new String[longs.length];
for (int i = 0; i < longs.length; i++) {
strings[i] = Converter.convertLong(longs[i]);
}
// Note: Comparator is not an option
Arrays.sort(longs);
Arrays.sort(strings);
final Pattern allowed = Pattern.compile("^[A-Za-z0-9]+$");
for (int i = 0; i < longs.length; i++) {
assertTrue("string: " + strings[i], allowed.matcher(strings[i]).matches());
assertEquals("string: " + strings[i], longs[i], Converter.parseLong(strings[i]));
}
}
以下是我正在寻找的方法:
public static class Converter {
public static String convertLong(final long value) {
// TODO
}
public static long parseLong(final String value) {
// TODO
}
}
我已经有一些解决这个问题的想法了,但我认为可能会从社区中得到一些好的(有创意的)建议。
此外,如果这个转换:
- 尽可能短
- 易于在其他语言中实现
编辑:我很高兴看到两位非常有声望的程序员遇到了和我一样的问题:使用“-”表示负数无法正常工作,因为“-”不能改变排序顺序:
- -0001
- -0002
- 0000
- 0001
- 0002
String.format
...哦,还有缺少线程(不)安全的免责声明。 - user85421String.format
,但是你需要解析它以便进行双向转换,所以最好使用一个方法完成。 - cletus