转换已知对象类型

时间:2013-08-24 23:27:22

标签: java casting

我正在开发一个允许您在数据库中创建产品的项目。它包含一个带有可编辑组合框的表单,因此您可以为新产品选择预先存在的制造商,或者键入要与产品一起创建的新制造商的名称。

组合框中填充了一组Manufacturer对象(它们实现了toString(),因此它们显示了一些有意义的东西)。

目前实现了处理组合框输出的逻辑:

Object mfr = mfctrCombo.getSelectedItem ();
Product newPrd = new Product ();

// If the mfr is a string then we need to create a new Manufacturer
if (mfr instanceof String) {
    Manufacturer newMfr = new Manufacturer ();
    newMfr.setName ((String) mfr);
    // Logic for persisting the new Manufacturer goes here
    newPrd.setManufacturer (newMfr);
} else if (mfr instanceof Manufacturer) {
    newPrd.setManufacturer ((Manufacturer) mfr);
}
// Logic for persisting the new Product goes here

这确实有效,但是我不需要投射mfr对象。我正在if块的开头做一个instanceof检查,所以我知道对象在块内的类型。在开始检查之后是否真的有必要在块内进行转换?在我看来,它不应该被要求。

虽然我是Java的新手,但我很确定我使用组合框做的事情不是最佳实践,而是因为它适用于具有截止日期的大学项目,因为它似乎有效为了这个目的,我宁愿留下讨论更好的方法来填充另一个问题的组合框。

4 个答案:

答案 0 :(得分:1)

你仍然必须强制转换实例,但是首先使用instanceof进行测试意味着编译器不会引发未经检查的强制转换警告,也意味着如果运行java.lang.ClassCastException,您将不会感到惊讶。事实证明这是你没想到的事情。

答案 1 :(得分:1)

是的,这是必需的。这使得必须实现java编译器的程序员更容易。如果要实现这个功能,他们将不得不经历大量的痛苦,编写代码以确定特定对象是否通过if语句保证是特定类型,没有人愿意做,以及没有它,java编译器将保持完美的功能。另外,可能没有人想到它。

所以,抱歉,如果没有演员表,没有理智的方法可以做到这一点。

答案 2 :(得分:0)

如果它不是String的实例,则不会仅转到if块。 因此,如果您的代码中有部分内容,则无需投放。

答案 3 :(得分:0)

如果您使用的是java 7,我认为有一个没有instanceof和强制转换的解决方案:

ComboBoxModel<Manufacturer> model = new DefaultComboBoxModel<>();
// Initialize model with existing manufacturers model.addElement(...)
JComboBox<Manufacturer> mfctrCombo = new JComboBox<>(model);

// ...

int selectedIndex = mfctrCombo.getSelectedIndex();
Product newPrd = new Product ();

if (selectedIndex == -1) {
    // The user provided a string then we need to create a new Manufacturer    
    Manufacturer newMfr = new Manufacturer ();
    newMfr.setName (mfctrCombo.getSelectedItem().toString());
    // Logic for persisting the new Manufacturer goes here
    newPrd.setManufacturer (newMfr);
} else {
    ComboBoxModel<Manufacturer> model = mfctrCombo.getModel();
    newPrd.setManufacturer (model.getElementAt(selectedIndex);
}

此外,您不需要依赖toString()来显示GUI上的显示文本(toString()并不意味着以这种方式使用,在国际化的情况下会出现问题),您可以相反,请提供ListCellRenderer,如问题JComboBox setting label and value所示。