有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java树集排序不正确

我需要保留一个节点的排序列表,从第一个节点开始,然后得到所有相邻节点。第一个节点和所有其他节点都带有一个种子值,用于根据最低种子值确定下一个将使用哪个节点,一旦节点用于获取相邻节点,它将被标记为已使用,因此即使它具有最低种子,也不会再次扩展

我的问题是,使用的值似乎爬到顶部并完全停止搜索,因为在3次迭代之后,顶部节点将是一个不断扩展的使用过的节点。这是我的树集代码,也是一个数字逐渐上升的例子

private static TreeSet<Node> nodelist = new TreeSet<Node>(
        new Comparator<Node>() {
            @Override
            public int compare(Node o1, Node o2) {
                if (o1.totalVal > o2.totalVal) {
                    if (o2.isValid)
                        return +1;
                    else
                        return -1;
                } else if (o1.totalVal < o2.totalVal)
                    return -1;
                else
                    return 0;
            }
        });

这是每一组插入之后树集的迭代,第四组之后的所有内容都与第四组相同,因为没有新元素可以读取

first set
true, 37.24913792078372
true, 38.12142238654117
true, 38.57602191449718
true, 38.57658845611187
true, 39.427369179869515
false, 36.6742416417845

second set
true, 37.84689665786984
false, 37.24913792078372
true, 38.12142238654117
true, 38.57602191449718
true, 38.57658845611187
true, 39.18376618407356
true, 39.427369179869515
false, 36.6742416417845

third set
true, 38.4682957019364
false, 37.84689665786984
false, 37.24913792078372
true, 38.12142238654117
true, 38.57602191449718
true, 38.57658845611187
true, 39.18376618407356
true, 39.427369179869515
true, 39.814763008775685
false, 36.6742416417845

fourth set
false, 38.4682957019364
false, 37.84689665786984
false, 37.24913792078372
true, 38.12142238654117
true, 38.57602191449718
true, 38.57658845611187
true, 38.590228543643214
true, 39.11409973215888
true, 39.18376618407356
true, 39.427369179869515
true, 39.814763008775685
true, 40.469726317012984
false, 36.6742416417845

到目前为止,我推断它与树结构有关,但我真的不明白它为什么这样做。我曾经尝试过对priorityqueue使用类似的方法,并对arraylist实现进行了排序,但两者都做了相同的操作,尽管它们在停止之前会再进行大约2次迭代

有什么帮助吗


共 (2) 个答案

  1. # 1 楼答案

    {}的合同要求比较是稳定的,即如果{}那么{}等等。看起来你没有这样做。我怀疑您应该以某种方式在else块中测试o1.isvalid,但没有足够的代码来确定

    你可能会更喜欢这样的东西:

    private static TreeSet<Node> nodelist = new TreeSet<Node>(
            new Comparator<Node>() {
                @Override
                public int compare(Node o1, Node o2) {
                    if ( o1.isValid == o2.isValid ) {
                        // Both valid/invalid - it's the totals that control the order.
                        return o1.totalVal - o2.totalVal;
                    } else {
                        // One valid, one not, move all invalids to one end.
                        return o1.isValid ? -1 : 1;
                    }
                }
            });
    
  2. # 2 楼答案

    您可能应该避免尝试编写自己的比较方法,因为它们可能很难推理。与Google Guava一起:

    private static final TreeSet<Node> treeSet = new TreeSet<>(nodeOrdering);
    

    其中nodeOrdering定义为:

    Comparator<Node> nodeOrdering = Ordering.natural()
        .onResultOf(isValidFunction)
        .compound(Ordering.natural().onResultOf(totalValueFunction));
    

    isValidFunction的定义如下:

    Function<Node, Boolean> isValidFunction = new Function<>() {
      @Override public Boolean apply(Node input) { return input.isValid; }
    };
    

    totalValueFunction的定义类似:

    Function<Node, Double> totalValueFunction = new Function<>() {
      @Override public Double apply(Node input) { return input.totalVal; }
    };