java 关键字使用实例
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/6601132/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
instanceof keyword usage
提问by aps
Is using the instanceof
keyword against the essence of object oriented programming
?
I mean is it a bad programming practice?
I read somewhere that using instanceof
keyword means that the design may not be that good. Any better workaround?
使用instanceof
关键字是否违背了本质object oriented programming
?我的意思是这是一种糟糕的编程习惯吗?我在某处读到使用instanceof
关键字意味着设计可能不是那么好。有什么更好的解决方法吗?
回答by thomson_matt
Generally speaking yes. It's best to keep all code that depends on being a specific class within that class, and using instanceof
generally means that you've put some code outside that class.
一般来说是的。最好将所有依赖于特定类的代码保留在该类中,使用instanceof
通常意味着您已将一些代码放在该类之外。
Look at this very simple example:
看这个非常简单的例子:
public class Animal
{
}
public class Dog extends Animal
{
}
public class Cat extends Animal
{
}
public class SomeOtherClass
{
public abstract String speak(Animal a)
{
String word = "";
if (a instanceof Dog)
{
word = "woof";
}
else if (a instanceof Cat)
{
word = "miaow";
}
return word;
}
}
Ideally, we'd like all of the behaviour that's specific to dogs to be contained in the Dog class, rather than spread around our program. We can change that by rewriting our program like this:
理想情况下,我们希望所有特定于狗的行为都包含在 Dog 类中,而不是散布在我们的程序中。我们可以通过像这样重写我们的程序来改变它:
public abstract class Animal
{
public String speak();
}
public class Dog extends Animal
{
public String speak()
{
return "woof";
}
}
public class Cat extends Animal
{
public String speak()
{
return "miaow";
}
}
public class SomeOtherClass
{
public String speak(Animal a)
{
return a.speak();
}
}
We've specified that an Animal
has to have a speak
method. Now SomeOtherClass
doesn't need to know the particular details of each type of animal - it can hand that off to the subclass of Animal
.
我们已经指定 anAnimal
必须有一个speak
方法。现在SomeOtherClass
不需要知道每种动物的特定细节 - 它可以将其传递给Animal
.
回答by arataj
There are many good answers promoting virtual methods, but instanceof
has its uses as well. Imagine that you iterate over List<Event>
, to pick up all Urgent
objects. You might do it using isUrgent()
but I am not sure if it were necessarily more concise or readable. Also, isUrgent()
would require making Event
aware that its subclasses may possess the respective property, which might:
有许多促进虚拟方法的好答案,但instanceof
也有其用途。想象一下,您遍历List<Event>
, 以获取所有Urgent
对象。你可以使用它来做,isUrgent()
但我不确定它是否一定更简洁或更易读。此外,isUrgent()
需要Event
注意其子类可能拥有各自的属性,这可能:
Event
belongs to some library that can not be modified.Event
属于一些不能修改的库。回答by Neil Coffey
The key is to not see instanceof as being part of common "normal practice". Like introspection in general, instanceof is a special tool for use in particular, atypical circumstances. Whenever you do use 'instanceof', you may also find yourself using other 'special' parts of the platform such as reflection more generally.
关键是不要将 instanceof 视为常见“常规做法”的一部分。与一般的内省一样,instanceof 是一种特殊的工具,用于特殊的非典型情况。每当您使用“instanceof”时,您可能还会发现自己使用了平台的其他“特殊”部分,例如更普遍的反射。
So long as whenever you find yourself using it you accept that what you're doing is a kludge in the absence of a more elegant/practical alternative, then that's fine.
只要你发现自己在使用它时,你接受在没有更优雅/实用的替代方案的情况下,你正在做的事情是杂乱无章的,那就没问题了。
That said, the most typical circumstances in everyday programs are probably:
也就是说,日常节目中最典型的情况可能是:
- implementing equals()
- reading serialized objects
- a few other cases where you're given an array/collection of items, e.g. enumerating JComponents in a frame/container and then taking action depending on type.
- 实现 equals()
- 读取序列化对象
- 在其他一些情况下,您会获得一个数组/项目集合,例如枚举框架/容器中的 JComponents,然后根据类型采取行动。
A rule of thumb you could try and stick to is to not require users of a library to have to use 'instanceof', but rather have any cases of 'instanceof' internal to the library.
您可以尝试并坚持的一条经验法则是,不要求库的用户必须使用“instanceof”,而是在库内部使用“instanceof”的任何情况。
Or put another way, you should re-frame your question: "What are the cases that 'intsanceof' is a workaround for?"
或者换一种说法,你应该重新帧您的问题:“什么是案件‘intsanceof’是一个解决办法的?”
回答by mre
Favor polymorphism and dynamic binding to downcasting and instanceof
. This is the "OO Way" and enables you to write code that doesn't need to know about subtypes.
倾向于多态性和动态绑定到向下转换和instanceof
. 这是“OO 方式”,使您能够编写不需要了解子类型的代码。
EXAMPLE
例子
abstract class Animal {
public abstract void talk();
//...
}
class Dog extends Animal {
public void talk() {
System.out.println("Woof!");
}
//...
}
class Cat extends Animal {
public void talk() {
System.out.println("Meow!");
}
//...
}
class Hippopotamus extends Animal {
public void talk() {
System.out.println("Roar!");
}
//...
}
class Main {
public static void main(String[] args) {
makeItTalk(new Cat());
makeItTalk(new Dog());
makeItTalk(new Hippopotamus());
}
public static void makeItTalk(Animal animal) {
animal.talk();
}
}
回答by Victor Sorokin
Usage of instanceof
is discouraged when same effect can be achieved via virtual methods, like in example of thomson_matt.
However, it's necessary to use instanceof
in some circumstances. For example, when your code gets Object from external source, say, network or third-party API which returns Object
, and you must decide what is the type of this Object and act appropriately.
instanceof
当可以通过虚拟方法实现相同的效果时,不鼓励使用 ,例如 thomson_matt 的示例。但是,instanceof
在某些情况下需要使用。例如,当您的代码从外部来源获取 Object 时,例如,返回 的网络或第三方 API Object
,您必须确定此 Object 的类型并采取适当的行动。
回答by tskuzzy
It's discouraged because people might use it to do something like this:
不鼓励这样做,因为人们可能会用它来做这样的事情:
if( myAnimal instanceof Dog )
((Dog)myAnimal).bark();
else( myAnimal instanceof Cat )
((Cat)myAnimal).meow();
Instead, Animal
should have a speak()
method which Dog
and Cat
inherit. In proper OOP with polymorphism and dynamic binding, you would then simply do
相反,Animal
应该有一个speak()
方法,它Dog
和Cat
继承。在具有多态性和动态绑定的适当 OOP 中,您只需执行
myAnimal.speak();
However, there are some instances in which you must use instanceof
to determine the specific type of an object. Perhaps you have a list of Animals
in your house and the only ones you want to take out for a walk()
are the Dog
s. In that case you would iterate through your list and only walk()
the dogs.
但是,您必须使用某些实例instanceof
来确定对象的特定类型。也许您Animals
的房子里有一个清单,而您想要取出的唯一清单walk()
是Dog
s。在这种情况下,您将遍历您的列表,并且只遍历walk()
狗。
回答by Thor
How about in the case of a creation factory (See below)? In this case, I don't think it is appropriate for an Animal subclass to know how to build a cage for itself. It seems out of out of scope of what an Animal is and forces the Animal subclass to take on behaviors that are not intrinsic to what an Animal is.
如果是创世工厂(见下文)呢?在这种情况下,我认为让 Animal 子类知道如何为自己建造笼子是不合适的。这似乎超出了 Animal 的范围,并强制 Animal 子类采取非 Animal 固有的行为。
public static Cage createCage(Animal animal) {
if (animal instanceof Dog)
return new DogHouse();
else if (animal instanceof Lion)
return new SteelCage();
else if (animal instanceof Chicken)
return new ChickenWiredCage();
else if (animal instanceof AlienPreditor)
return new ForceFieldCage();
...
else
return new GenericCage();
}
回答by djuRa
Another usage of instaceOf operation could be error handling. If you have similar error handling for exceptions, and you want to have it all in one place you can use:
instaceOf 操作的另一个用途可能是错误处理。如果您对异常有类似的错误处理,并且希望将所有内容集中在一处,则可以使用:
public void handleError(Throwable t, HttpServletRequest req) {
if (t instaceOf ValidationException) {
...doSomewthing......
} else if (t instaceOf DataException) {
...doSomewthing......
} else if (t instaceOf DataException) {
...doSomewthing......
} else {
...doSomewthing......
}
}
with above code, you avoid to have many
使用上面的代码,你可以避免有很多
} catch <Exception> {
blocks and instead have just one
块,而是只有一个
} catch (Throwable t) {
handleError(t, request);
return "errorPage" or whateveryouwant;
}
Also, one more thing is, is you check java source code, you will find so many usages of instaceof..
另外,还有一件事是,如果你检查java源代码,你会发现instaceof..的很多用法。
And one good link: article about usage of instaceof
还有一个很好的链接: 关于 instaceof 用法的文章