【问题标题】:Java PriorityQueue appears to be in the wrong order [duplicate]Java PriorityQueue 似乎顺序错误[重复]
【发布时间】:2015-10-29 03:17:31
【问题描述】:

我正在尝试制作一个解决最小生成树问题的程序。为此,我有一个边缘对象的优先级队列,应该根据它们相应的权重字段进行排序(之后并不重要,但我一直在按节点名称进行排序)。

我正在使用java.util.PriorityQueue。我已经尝试了几乎所有方法,但我无法想到实现compareTo() 函数的工作原理。它对大多数边缘进行正确排序,但不是全部。这是我能想到的最基本的compareTo() 函数的代码:

@Override
public int compareTo(Object other) {
    return toString().compareTo(((Edge) other).toString());
}

toString() 函数首先输出权重,然后是两个节点,因此如果两个节点 A 和 B 以权重 4 连接,它将输出

4AB

放入示例图后,我最终得到以下优先级队列:

[1AB, 1BA, 1FH, 2CB, 1CG, 1GC, 1HF, 2EB, 2CD, 3EG, 2BC, 2BE, 3AC, 2GH, 2HG, 5AD, 5EC, 3ED, 2EF, 5CE, 4FD, 2FE, 4FG, 5DA, 2DC, 3GE, 4GF, 3DE, 3CA, 4DF]

显然这不是按顺序排列的,但基本上我能想到的所有比较方法都会产生这个结果。

【问题讨论】:

  • 您能否发布更多代码,包括节点类、将事物放入队列的位置以及最终结果列表的方式?
  • 发布您用来显示队列的代码。我会向甜甜圈打赌你的问题就在那里。如果您使用检索方法打印出值,您将得到正确的顺序。
  • 如果您指的是 Java 的内置优先级队列,请查看:stackoverflow.com/questions/5695017/…
  • @BartKiers Err 是的,我的意思是获取它们的正确方法;)
  • 请注意,顺便说一下,您的基于字符串的比较存在固有缺陷,因为它无法正确处理大于 9 的权重。这并不能解释您呈现的特定错误排序,但它是一个很好的理由来构建一个正确的compareTo()(或一个正确的Comparator实现)来执行真正的数字比较。

标签: java priority-queue compareto minimum-spanning-tree


【解决方案1】:

这里没有错。您正在打印的内容似乎是 toString() 的结果,不能保证按任何特定顺序打印。

但是,当您通过移除或查看头部来消耗队列时,将产生一个由比较器定义的最小元素。整个队列是无序的;顺序只决定队列的head,只有指定对头部进行操作的某些操作受顺序影响。 toString()iterator() 方法不在这些操作中。

您的比较器应该以数字方式比较权重,而不是字符串。使用边缘的字符串比较作为具有相同权重的边缘的决胜局是可以的,但请考虑您是否会有两个方向相反的边缘,以及它们是否需要特别小心。

【讨论】:

  • @MaxZoom 我指的是PriorityQueuetoString()方法(继承自AbstractCollection)。
猜你喜欢
  • 2013-07-15
  • 1970-01-01
  • 1970-01-01
  • 2011-12-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-12-04
相关资源
最近更新 更多