我开发了一个Java模块,用于检查JFrame表单上的任何组件是否已更改其值(文本),并将组件放入JFrame的HashSet中。
目前,当值/文本发生变化时,我将组件名称(String type)放入HashSet中。
我还想到如果我将Object(具有更改值的组件)放入HashSet中,认为与使用组件名称(String)相比,它可以节省时间。
在这里,我的问题是哪个更快/更有效率
总之,也许,哪个更便宜?字符串比较或对象比较?
谢谢,
JB
答案 0 :(得分:1)
Martin的回答是正确的,不要担心性能问题,除非您确定自己有严重的性能问题,这会对您的产品产生实际的负面影响。
但要回答这个问题:
如果您使用stands_query.equalTo(“stadiumId”,stadium);
,则性能取决于组件是否实现HashSet
,如果是,则hashCode()
计算的成本是多少。最有可能的是他们甚至没有实现hashCode()
,所以他们的哈希码基本上是他们的身份哈希码,(查找),所以把对象放在地图而不是字符串将无限快。我们在这里谈论时钟周期。
这同样适用于比较:组件可能也没有实现hashCode()
,因此它们将通过引用进行比较,这比比较字符串要快一些。
如果"可能"对你来说不够好,如果你不能查看这些组件的源代码,那么你可以使用equals()
而不是IdentityHashSet
来保证只有身份哈希码和引用比较才能使用。
但是谁在乎呢。到目前为止,最好的方法是做一些更简单,更易理解,更易于维护的方法。
答案 1 :(得分:0)
插入的便宜性不应成为开发阶段的首要考虑因素。 equals
方法对于对象执行通常并不昂贵。您应该从提供最少代码复杂性的任何事情开始,只有在性能成为问题时才开始定位效率。此外,除非hashcode
项中插入的项目发生冲突,否则甚至不会进行比较。
答案 2 :(得分:0)
我刚刚在Java中测试了我自己的两个HashSet元素类型的选择。 结果说出我想的一切。
HashSet element type: Object, experiment count: 1000, Elapsed time: 16ms
HashSet element type: Object, experiment count: 1000, Elapsed time: 8ms
HashSet element type: Object, experiment count: 1000, Elapsed time: 8ms
HashSet element type: String, experiment count: 1000, Elapsed time: 124ms
HashSet element type: String, experiment count: 1000, Elapsed time: 110ms
HashSet element type: String, experiment count: 1000, Elapsed time: 130ms
你知道,Java的执行速度仍然有一些不好的声誉。 你会使用什么样的HashSet元素类型?
以下是我的代码,显示了上述结果。
boolean StringUsed = true;
changedComponents = new HashSet<Component>() {};
changedComponentNames = new HashSet<String>() {};
private void changeValueManyTimes() {
long start = System.currentTimeMillis();
for (int i = 0; i<count; i++) {
recordStatisticsCheckBox.setSelected
(!recordStatisticsCheckBox.isSelected());
}
long stop = System.currentTimeMillis();
System.out.print("HashSet element type: " +
(StringUsed ? "String" : "Object") + ", experiment count: " + count);
System.out.println(", Elapsed time: " + (stop - start) + "ms");
System.out.println("");
}
public static int count = 1000;
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
StringUsed = false;
changeValueManyTimes();
}
private void recordStatisticsCheckBoxStateChanged
(javax.swing.event.ChangeEvent evt) {
recordStatisticsCheckBoxActionPerformed(null);
}
private void jButton2ActionPerformed(java.awt.event.ActionEvent evt) {
StringUsed = true;
changeValueManyTimes();
}
private void recordStatisticsCheckBoxActionPerformed
(java.awt.event.ActionEvent evt) {
if (StringUsed) {
if (recordStatisticsCheckBox.isSelected() == origSelection) {
changedComponents.remove(recordStatisticsCheckBox);
} else {
changedComponents.add(recordStatisticsCheckBox);
}
changeSaveEnabledIfNeeded();
} else {
if (recordStatisticsCheckBox.isSelected() == origSelection) {
changedComponentNames.remove(recordStatisticsCheckBox.getName());
} else {
changedComponentNames.add(recordStatisticsCheckBox.getName());
}
changeSaveEnabledIfNeeded();
}
}
private void changeSaveEnabledIfNeeded() {
if (changedComponents.size() == 0)
saveButton.setEnabled(false);
else
saveButton.setEnabled(true);
}