【问题标题】:How to sort a String list by using part of its numerical contents?如何使用部分数字内容对字符串列表进行排序?
【发布时间】:2016-03-18 11:31:29
【问题描述】:

我正在尝试对ArrayList<String> 进行排序。列表中的字符串看起来像这样"abc 123 def 456",我想对列表进行排序,使最后一个数字最小的字符串排在第一位,例如如果元素是

{"abc 123 def 456", "ghi 456 jkl 789", "mno 101 pqr 112"}

然后我希望排序列表首先有第三个字符串,然后是第一个字符串,然后是第二个字符串。

{"mno 101 pqr 112", "abc 123 def 456","ghi 456 jkl 789"}

就像这样。

我尝试使用 list.split(" ")Double.parseDouble(String)Collections.sort(list) 对其进行排序,但我现在不知道如何将剩余的字符串与排序后的数字列表正确连接。

编辑:

String[] numbers = list.get(i).split(" ");
numberList.add(Integer.parseInt(numbers[3]));
Collections.sort(numberList);

现在我知道数字应该如何排序,但我无法将它们与“他们的字符串”的其余部分重新连接。

【问题讨论】:

  • 向我们展示您的最佳尝试。不要使用 Double.parseDouble() 来解析整数。
  • 只需按最后一个数字排序,您不会强制分隔字符串的各个部分,所以不要这样做。为什么要让你的生活更艰难?
  • @JBNizet 也许你可以解释一下用 parseDouble 解析整数的缺点是什么?
  • 我的实际字符串包含双精度而不是整数,这也是我在这里写 Double.parseDouble() 的原因。 @Peter Lawrey我希望字符串在排序后是相同的,只是以其他顺序。我还能按最后一个数字排序吗?
  • Double.parseDouble() 需要一个十进制数,而您需要一个整数。因此,如果您正在解析的内容恰好是有效的双精度数,它会很高兴地返回一个值,尽管它应该只接受有效的整数。例如, parseDouble() 将愉快地解析“1.23e7”,尽管这显然不是您所期望的,并且您最好有一个异常,表明错误,如果这是您实际解析的内容。如果您需要一个整数,请解析一个整数。

标签: java string sorting arraylist


【解决方案1】:

使用自定义Comparator 的简单解决方案:

String[] arr = {"abc 123 def 456", "ghi 456 jkl 789", "mno 101 pqr 112"};

Arrays.sort(arr, new Comparator<String>() {
    @Override
    public int compare(String o1, String o2) {
        return getLastNum(o1) - getLastNum(o2);
    }

    private int getLastNum(String s) {
        String[] tokens = s.split(" ");
        return Double.parseDouble(tokens[tokens.length - 1]);
    }
});

希望这段代码是不言自明的。

【讨论】:

    【解决方案2】:

    如果所有的格式相同,则解析String#split结果的最后一个字符串并比较这些值。

    list.sort((s1, s2) -> {
        String[] split1 = s1.split("\\s+");
        String[] split2 = s2.split("\\s+");
        return Double.compare(
            Double.parseDouble(split1[split1.length - 1]),
            Double.parseDouble(split2[split2.length - 1]);
    });
    

    或者按照@JBNizet 的建议:

    list.sort(Comparator.comparingDouble(s -> Double.parseDouble(s.substring(s.lastIndexOf(' ') + 1))));
    

    【讨论】:

    • 或者,使用 Java 8:list.sort(Comparator.comparingDouble(s -&gt; Double.parseDouble(s.substring(s.lastIndexOf(' ') + 1))));。喜欢那些简单的单线。
    • 您在答案中混淆了 split1 和 split2:split2[split1.length - 1]
    • 它们的顺序仍然错误。您的比较器以相反的顺序排序。这是 Comparator.comparing() 的好处之一:你不会弄乱参数的顺序,因为你只有一个。
    • 我误读了这个问题,我(不知道为什么)虽然 OP 正在寻找逆序。
    • 恐怕我不太了解您的代码。 String#split 是什么? s1 和 s2 呢?那些是列表中的字符串吗?
    猜你喜欢
    • 2017-11-20
    • 2014-02-21
    • 2019-07-13
    • 2011-03-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多