动态语言中的接口有什么意义吗?

时间:2021-04-11 11:34:19

In static languages like Java you need interfaces because otherwise the type system just won't let you do certain things. But in dynamic languages like PHP and Python you just take advantage of duck-typing.

在像Java这样的静态语言中,你需要接口,否则类型系统就不会让你做某些事情。但是在像PHP和Python这样的动态语言中,你只需要利用duck-typing。

PHP supports interfaces. Ruby and Python don't have them. So you can clearly live happily without them.

PHP支持接口。 Ruby和Python没有它们。所以你可以在没有他们的情况下幸福地生活。

I've been mostly doing my work in PHP and have never really made use of the ability to define interfaces. When I need a set of classes to implement certain common interface, then I just describe it in documentation.

我一直在用PHP完成我的工作,从来没有真正使用定义接口的能力。当我需要一组类来实现某些通用接口时,我只是在文档中描述它。

So, what do you think? Aren't you better off without using interfaces in dynamic languages at all?

所以你怎么看?如果不使用动态语言中的接口,你不是更好吗?

17 个解决方案

#1


17  

I think of it more as a level of convenience. If you have a function which takes a "file-like" object and only calls a read() method on it, then it's inconvenient - even limiting - to force the user to implement some sort of File interface. It's just as easy to check if the object has a read method.

我认为它更像是一种便利。如果你有一个函数,它接受一个“类文件”对象并且只调用read()方法,那么强迫用户实现某种File接口是不方便的 - 甚至是限制。检查对象是否具有读取方法同样容易。

But if your function expects a large set of methods, it's easier to check if the object supports an interface then to check for support of each individual method.

但是,如果您的函数需要大量方法,则更容易检查对象是否支持接口,然后检查每个方法的支持。

#2


10  

Yes, there is a point

是的,有一点

If you don't explicitly use interfaces your code still uses the object as though it implemented certain methods it's just unclear what the unspoken interface is.

如果你没有显式地使用接口,你的代码仍然使用该对象,就好像它实现了某些方法一样,它只是不清楚未说出的接口是什么。

If you define a function to accept an interface (in PHP say) then it'll fail earlier, and the problem will be with the caller not with the method doing the work. Generally failing earlier is a good rule of thumb to follow.

如果你定义一个函数来接受一个接口(在PHP中说),那么它将会提前失败,问题将出在调用者身上而不是使用该方法完成工作。一般来说,早先失败是一个很好的经验法则。

#3


9  

Interfaces actually add some degree of dynamic lang-like flexibility to static languages that have them, like Java. They offer a way to query an object for which contracts it implements at runtime.

接口实际上为具有它们的静态语言添加了一定程度的动态类似灵活性,如Java。它们提供了一种查询对象的方法,该对象在运行时实现了这些对象。

That concept ports well into dynamic languages. Depending on your definition of the word "dynamic", of course, that even includes Objective-C, which makes use of Protocols pretty extensively in Cocoa.

这个概念很好地融入了动态语言。当然,根据您对“动态”一词的定义,甚至包括Objective-C,它在Cocoa中广泛使用Protocols。

In Ruby you can ask whether an object responds to a given method name. But that's a pretty weak guarantee that it's going to do what you want, especially given how few words get used over and over, that the full method signature isn't taken into account, etc.

在Ruby中,您可以询问对象是否响应给定的方法名称。但这是一个非常微弱的保证,它会做你想要的,特别是考虑到一遍又一遍地使用了很少的单词,没有考虑完整的方法签名等。

In Ruby I might ask

在Ruby中我可能会问

object.respond_to? :sync

So, yeah, it has a method named "sync", whatever that means.

所以,是的,它有一个名为“sync”的方法,无论那意味着什么。

In Objective-C I might ask something similar, i.e. "does this look/walk/quack like something that synchronizes?":

在Objective-C中,我可能会问类似的东西,即“看起来/走路/嘎嘎像是同步的东西吗?”:

[myObject respondsToSelector:@selector(sync)]

Even better, at the cost of some verbosity, I can ask something more specific, i.e. "does this look/walk/quack like something that synchronizes to MobileMe?":

更好的是,以一些冗长的代价,我可以提出一些更具体的内容,即“看起来/走路/嘎嘎就像是与MobileMe同步的东西?”:

[myObject respondsToSelector:@selector(sync:withMobileMeAccount:)]

That's duck typing down to the species level.

这是鸭子打字到物种水平。

But to really ask an object whether it is promising to implement synchronization to MobileMe...

但要真正问一个对象是否有希望实现与MobileMe的同步...

[receiver conformsToProtocol:@protocol(MobileMeSynchronization)]

Of course, you could implement protocols by just checking for the presence of a series of selectors that you consider the definition of a protocol/duck, and if they are specific enough. At which point the protocol is just an abbreviation for a big hunk of ugly responds_to? queries, and some very useful syntactic sugar for the compiler/IDE to use.

当然,您可以通过检查您认为是协议/ duck的定义的一系列选择器的存在来实现协议,以及它们是否足够具体。在这一点上,协议只是一大堆丑陋的responds_to的缩写?查询,以及编译器/ IDE使用的一些非常有用的语法糖。

Interfaces/protocols are another dimension of object metadata that can be used to implement dynamic behavior in the handling of those objects. In Java the compiler just happens to demand that sort of thing for normal method invocation. But even dynamic languages like Ruby, Python, Perl, etc. implement a notion of type that goes beyond just "what methods an object responds to". Hence the class keyword. Javascript is the only really commonly used language without that concept. If you've got classes, then interfaces make sense, too.

接口/协议是对象元数据的另一个维度,可用于在处理这些对象时实现动态行为。在Java中,编译器恰好要求正常的方法调用。但即使是像Ruby,Python,Perl等动态语言也实现了一种超越“对象响应的方法”的类型概念。因此class关键字。 Javascript是没有这个概念的唯一真正常用的语言。如果你有课程,那么接口也是有意义的。

It's admittedly more useful for more complicated libraries or class hierarchies than in most application code, but I think the concept is useful in any language.

对于更复杂的库或类层次结构而言,它比大多数应用程序代码更有用,但我认为这个概念在任何语言中都很有用。

Also, somebody else mentioned mixins. Ruby mixins are a way to share code -- e.g., they relate to the implementation of a class. Interfaces/protocols are about the interface of a class or object. They can actually complement each other. You might have an interface which specifies a behavior, and one or more mixins which help an object to implement that behavior.

另外,还有人提到了mixins。 Ruby mixins是一种共享代码的方式 - 例如,它们与类的实现有关。接口/协议是关于类或对象的接口。它们实际上可以相互补充。您可能有一个指定行为的接口,以及一个或多个帮助对象实现该行为的mixin。

Of course, I can't think of any languages which really have both as distinct first-class language features. In those with mixins, including the mixin usually implies the interface it implements.

当然,我想不出任何真正具有独特的一流语言特征的语言。在mixins中,包括mixin通常意味着它实现的接口。

#4


4  

If you do not have hight security constraints (so nobody will access you data a way you don't want to) and you have a good documentation or well trained coders (so they don't need the interpreter / compiler to tell them what to do), then no, it's useless.

如果你没有高安全性限制(所以没有人会以你不想要的方式访问你的数据)并且你有一个好的文档或训练有素的编码器(所以他们不需要解释器/编译器来告诉他们该怎么做do),然后不,它没用。

For most medium size projects, duck typing is all you need.

对于大多数中型项目,只需要鸭子打字。

#5


3  

I was under the impression that Python doesn't have interfaces. As far as I'm aware in Python you can't enforce a method to be implemented at compilation time precisely because it is a dynamic language.

我的印象是Python没有接口。据我所知,在Python中你无法强制执行在编译时实现的方法,因为它是一种动态语言。

There are interface libraries for Python but I haven't used any of them.

有Python的接口库,但我没有使用它们中的任何一个。

Python also has Mixins so you could have create an Interface class by defining a Mixin an having pass for every method implementation but that's not really giving you much value.

Python也有Mixins,所以你可以通过为每个方法实现定义一个具有传递的Mixin来创建一个Interface类,但这并不能给你带来太多价值。

#6


3  

I think use of interfaces is determined more by how many people will be using your library. If it's just you, or a small team then documentation and convention will be fine and requiring interfaces will be an impediment. If it's a public library then interfaces are much more useful because they constrain people to provide the right methods rather than just hint. So interfaces are definitely a valuable feature for writing public libraries and I suppose that lack (or at least de-emphasis) is one of the many reasons why dynamic languages are used more for apps and strongly-typed languages are used for big libraries.

我认为接口的使用更多地取决于有多少人将使用您的库。如果它只是你,或者是一个小团队,那么文档和惯例就会很好,并且要求接口将是一个障碍。如果它是一个公共库,那么接口更有用,因为它们限制人们提供正确的方法而不仅仅提示。因此,接口绝对是编写公共库的一个有价值的特性,我认为缺乏(或至少不再强调)是动态语言更多地用于应用程序而强类型语言用于大型库的众多原因之一。

#7


2  

Rene, please read my answer to "Best Practices for Architecting Large Systems in a Dynamic Language" question here on *. I discuss some benefits of giving away the freedom of dynamic languages to save development effort and to ease introducing new programmers to the project. Interfaces, when used properly, greatly contribute to writing reliable software.

Rene,请在*上阅读我对“动态语言中构建大型系统的最佳实践”问题的回答。我讨论了放弃动态语言*以节省开发工作和简化新程序员引入项目的一些好处。如果使用得当,接口极大地有助于编写可靠的软件。

#8


2  

In a language like PHP where a method call that doesn't exist results in a fatal error and takes the whole application down, then yes interfaces make sense.

在像PHP这样的语言中,不存在的方法调用会导致致命错误并使整个应用程序失效,那么yes接口是有意义的。

In a language like Python where you can catch and handle invalid method calls, it doesn't.

在Python这样的语言中,您可以捕获并处理无效的方法调用,但事实并非如此。

#9


2  

Python 3000 will have Abstract Base Classes. Well worth a read.

Python 3000将具有抽象基类。非常值得一读。

#10


1  

One use of the Java "interface" is to allow strongly-typed mixins in Java. You mix the proper superclass, plus any additional methods implemented to support the interface.

Java“接口”的一个用途是允许Java中的强类型mixin。您可以混合使用适当的超类,以及为支持该接口而实现的任何其他方法。

Python has multiple inheritance, so it doesn't really need the interface contrivance to allow methods from multiple superclasses.

Python具有多重继承,因此它不需要接口设计来允许来自多个超类的方法。

I, however, like some of the benefits of strong typing -- primarily, I'm a fan of early error detection. I try to use an "interface-like" abstract superclass definition.

然而,我喜欢强类型的一些好处 - 主要是,我是早期错误检测的粉丝。我尝试使用“类似接口”的抽象超类定义。

class InterfaceLikeThing( object ):
    def __init__( self, arg ):
        self.attr= None
        self.otherAttr= arg
    def aMethod( self ):
        raise NotImplementedError
    def anotherMethod( self ):
        return NotImplemented

This formalizes the interface -- in a way. It doesn't provide absolute evidence for a subclass matching the expectations. However, if a subclass fails to implement a required method, my unit tests will fail with an obvious NotImplemented return value or NotImplementedError exception.

这在某种程度上正式化了界面。它没有为符合期望的子类提供绝对证据。但是,如果子类未能实现所需的方法,则单元测试将失败,并显示明显的NotImplemented返回值或NotImplementedError异常。

#11


0  

Well, first of all, it's right that Ruby does not have Interface as is, but they have mixin, wich takes somehow the best of both interfaces and abstract classes from other languages.

好吧,首先,Ruby没有接口是正确的,但是他们有mixin,它在某种程度上是两种接口和其他语言抽象类的最佳选择。

The main goal of interface is to ensure that your object SHALL implement ALL the methods present in the interface itself.

接口的主要目标是确保您的对象应该实现接口本身中存在的所有方法。

Of course, interface are never mandatory, even in Java you could imagine to work only with classes and using reflection to call methods when you don't know wich kind of object you're manipulating, but it is error prone and should be discouraged in many ways.

当然,接口永远不是强制性的,即使在Java中,你可以想象只使用类和使用反射来调用方法,当你不知道你正在操作的那种对象时,它很容易出错,应该不鼓励使用很多方法。

#12


0  

Well, it would certainly be easier to check if a given object supported an entire interface, instead of just not crashing when you call the one or two methods you use in the initial method, for instance to add an object to an internal list.

那么,检查给定对象是否支持整个接口肯定会更容易,而不是在调用初始方法中使用的一个或两个方法时不会崩溃,例如将对象添加到内部列表。

Duck typing has some of the benefits of interfaces, that is, easy of use everywhere, but the detection mechanism is still missing.

鸭子打字具有界面的一些好处,即易于使用,但检测机制仍然缺失。

#13


0  

It's like saying you don't need explicit types in a dynamically-typed language. Why don't you make everything a "var" and document their types elsewhere?

这就像说你不需要动态类型语言中的显式类型。为什么不把所有东西都变成“var”并在其他地方记录它们的类型?

It's a restriction imposed on a programmer, by a programmer. It makes it harder for you to shoot yourself in the foot; gives you less room for error.

这是程序员对程序员施加的限制。这让你更难以在脚下射击自己;为您提供更少的错误空间。

#14


0  

as a PHP programmer, the way I see it, an Interface is basically used as a contract. It lets you say that everything which uses this interface MUST implement a given set of functions.

作为一个PHP程序员,我看到它的方式,一个接口基本上用作合同。它可以让你说使用这个接口的一切必须实现一组给定的功能。

I dunno if that's all that useful, but I found it a bit of a stumbling block when trying to understand what Interfaces were all about.

我不知道这是否有用,但我发现在尝试理解接口的全部内容时,它有点绊脚石。

#15


0  

If you felt you had to, you could implement a kind of interface with a function that compares an object's methods/attributes to a given signature. Here's a very basic example:

如果你觉得必须这样做,你可以用一个函数来实现一种接口,该函数将对象的方法/属性与给定的签名进行比较。这是一个非常基本的例子:

file_interface = ('read', 'readline', 'seek')

class InterfaceException(Exception): pass

def implements_interface(obj, interface):
    d = dir(obj)
    for item in interface:
        if item not in d: raise InterfaceException("%s not implemented." % item)
    return True

>>> import StringIO
>>> s = StringIO.StringIO()
>>> implements_interface(s, file_interface)
True
>>> 
>>> fp = open('/tmp/123456.temp', 'a')    
>>> implements_interface(fp, file_interface)
True
>>> fp.close()
>>> 
>>> d = {}
>>> implements_interface(d, file_interface)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 4, in implements_interface
__main__.InterfaceException: read not implemented.

Of course, that doesn't guarantee very much.

当然,这并不能保证很多。

#16


0  

In addition to the other answers I just want to point out that Javascript has an instanceof keyword that will return true if the given instance is anywhere in a given object's prototype chain.

除了其他答案之外,我只想指出Javascript有一个instanceof关键字,如果给定实例在给定对象的原型链中的任何位置,它将返回true。

This means that if you use your "interface object" in the prototype chain for your "implementation objects" (both are just plain objects to JS) then you can use instanceof to determine if it "implements" it. This does not help the enforcement aspect, but it does help in the polymorphism aspect - which is one common use for interfaces.

这意味着如果您在原型链中使用“接口对象”作为“实现对象”(两者都只是JS的普通对象),那么您可以使用instanceof来确定它是否“实现”它。这对执行方面没有帮助,但它确实有助于多态方面 - 这是接口的一个常见用途。

MDN instanceof Reference

MDN instanceof参考

#17


-2  

Stop trying to write Java in a dynamic language.

停止尝试用动态语言编写Java。

#1


17  

I think of it more as a level of convenience. If you have a function which takes a "file-like" object and only calls a read() method on it, then it's inconvenient - even limiting - to force the user to implement some sort of File interface. It's just as easy to check if the object has a read method.

我认为它更像是一种便利。如果你有一个函数,它接受一个“类文件”对象并且只调用read()方法,那么强迫用户实现某种File接口是不方便的 - 甚至是限制。检查对象是否具有读取方法同样容易。

But if your function expects a large set of methods, it's easier to check if the object supports an interface then to check for support of each individual method.

但是,如果您的函数需要大量方法,则更容易检查对象是否支持接口,然后检查每个方法的支持。

#2


10  

Yes, there is a point

是的,有一点

If you don't explicitly use interfaces your code still uses the object as though it implemented certain methods it's just unclear what the unspoken interface is.

如果你没有显式地使用接口,你的代码仍然使用该对象,就好像它实现了某些方法一样,它只是不清楚未说出的接口是什么。

If you define a function to accept an interface (in PHP say) then it'll fail earlier, and the problem will be with the caller not with the method doing the work. Generally failing earlier is a good rule of thumb to follow.

如果你定义一个函数来接受一个接口(在PHP中说),那么它将会提前失败,问题将出在调用者身上而不是使用该方法完成工作。一般来说,早先失败是一个很好的经验法则。

#3


9  

Interfaces actually add some degree of dynamic lang-like flexibility to static languages that have them, like Java. They offer a way to query an object for which contracts it implements at runtime.

接口实际上为具有它们的静态语言添加了一定程度的动态类似灵活性,如Java。它们提供了一种查询对象的方法,该对象在运行时实现了这些对象。

That concept ports well into dynamic languages. Depending on your definition of the word "dynamic", of course, that even includes Objective-C, which makes use of Protocols pretty extensively in Cocoa.

这个概念很好地融入了动态语言。当然,根据您对“动态”一词的定义,甚至包括Objective-C,它在Cocoa中广泛使用Protocols。

In Ruby you can ask whether an object responds to a given method name. But that's a pretty weak guarantee that it's going to do what you want, especially given how few words get used over and over, that the full method signature isn't taken into account, etc.

在Ruby中,您可以询问对象是否响应给定的方法名称。但这是一个非常微弱的保证,它会做你想要的,特别是考虑到一遍又一遍地使用了很少的单词,没有考虑完整的方法签名等。

In Ruby I might ask

在Ruby中我可能会问

object.respond_to? :sync

So, yeah, it has a method named "sync", whatever that means.

所以,是的,它有一个名为“sync”的方法,无论那意味着什么。

In Objective-C I might ask something similar, i.e. "does this look/walk/quack like something that synchronizes?":

在Objective-C中,我可能会问类似的东西,即“看起来/走路/嘎嘎像是同步的东西吗?”:

[myObject respondsToSelector:@selector(sync)]

Even better, at the cost of some verbosity, I can ask something more specific, i.e. "does this look/walk/quack like something that synchronizes to MobileMe?":

更好的是,以一些冗长的代价,我可以提出一些更具体的内容,即“看起来/走路/嘎嘎就像是与MobileMe同步的东西?”:

[myObject respondsToSelector:@selector(sync:withMobileMeAccount:)]

That's duck typing down to the species level.

这是鸭子打字到物种水平。

But to really ask an object whether it is promising to implement synchronization to MobileMe...

但要真正问一个对象是否有希望实现与MobileMe的同步...

[receiver conformsToProtocol:@protocol(MobileMeSynchronization)]

Of course, you could implement protocols by just checking for the presence of a series of selectors that you consider the definition of a protocol/duck, and if they are specific enough. At which point the protocol is just an abbreviation for a big hunk of ugly responds_to? queries, and some very useful syntactic sugar for the compiler/IDE to use.

当然,您可以通过检查您认为是协议/ duck的定义的一系列选择器的存在来实现协议,以及它们是否足够具体。在这一点上,协议只是一大堆丑陋的responds_to的缩写?查询,以及编译器/ IDE使用的一些非常有用的语法糖。

Interfaces/protocols are another dimension of object metadata that can be used to implement dynamic behavior in the handling of those objects. In Java the compiler just happens to demand that sort of thing for normal method invocation. But even dynamic languages like Ruby, Python, Perl, etc. implement a notion of type that goes beyond just "what methods an object responds to". Hence the class keyword. Javascript is the only really commonly used language without that concept. If you've got classes, then interfaces make sense, too.

接口/协议是对象元数据的另一个维度,可用于在处理这些对象时实现动态行为。在Java中,编译器恰好要求正常的方法调用。但即使是像Ruby,Python,Perl等动态语言也实现了一种超越“对象响应的方法”的类型概念。因此class关键字。 Javascript是没有这个概念的唯一真正常用的语言。如果你有课程,那么接口也是有意义的。

It's admittedly more useful for more complicated libraries or class hierarchies than in most application code, but I think the concept is useful in any language.

对于更复杂的库或类层次结构而言,它比大多数应用程序代码更有用,但我认为这个概念在任何语言中都很有用。

Also, somebody else mentioned mixins. Ruby mixins are a way to share code -- e.g., they relate to the implementation of a class. Interfaces/protocols are about the interface of a class or object. They can actually complement each other. You might have an interface which specifies a behavior, and one or more mixins which help an object to implement that behavior.

另外,还有人提到了mixins。 Ruby mixins是一种共享代码的方式 - 例如,它们与类的实现有关。接口/协议是关于类或对象的接口。它们实际上可以相互补充。您可能有一个指定行为的接口,以及一个或多个帮助对象实现该行为的mixin。

Of course, I can't think of any languages which really have both as distinct first-class language features. In those with mixins, including the mixin usually implies the interface it implements.

当然,我想不出任何真正具有独特的一流语言特征的语言。在mixins中,包括mixin通常意味着它实现的接口。

#4


4  

If you do not have hight security constraints (so nobody will access you data a way you don't want to) and you have a good documentation or well trained coders (so they don't need the interpreter / compiler to tell them what to do), then no, it's useless.

如果你没有高安全性限制(所以没有人会以你不想要的方式访问你的数据)并且你有一个好的文档或训练有素的编码器(所以他们不需要解释器/编译器来告诉他们该怎么做do),然后不,它没用。

For most medium size projects, duck typing is all you need.

对于大多数中型项目,只需要鸭子打字。

#5


3  

I was under the impression that Python doesn't have interfaces. As far as I'm aware in Python you can't enforce a method to be implemented at compilation time precisely because it is a dynamic language.

我的印象是Python没有接口。据我所知,在Python中你无法强制执行在编译时实现的方法,因为它是一种动态语言。

There are interface libraries for Python but I haven't used any of them.

有Python的接口库,但我没有使用它们中的任何一个。

Python also has Mixins so you could have create an Interface class by defining a Mixin an having pass for every method implementation but that's not really giving you much value.

Python也有Mixins,所以你可以通过为每个方法实现定义一个具有传递的Mixin来创建一个Interface类,但这并不能给你带来太多价值。

#6


3  

I think use of interfaces is determined more by how many people will be using your library. If it's just you, or a small team then documentation and convention will be fine and requiring interfaces will be an impediment. If it's a public library then interfaces are much more useful because they constrain people to provide the right methods rather than just hint. So interfaces are definitely a valuable feature for writing public libraries and I suppose that lack (or at least de-emphasis) is one of the many reasons why dynamic languages are used more for apps and strongly-typed languages are used for big libraries.

我认为接口的使用更多地取决于有多少人将使用您的库。如果它只是你,或者是一个小团队,那么文档和惯例就会很好,并且要求接口将是一个障碍。如果它是一个公共库,那么接口更有用,因为它们限制人们提供正确的方法而不仅仅提示。因此,接口绝对是编写公共库的一个有价值的特性,我认为缺乏(或至少不再强调)是动态语言更多地用于应用程序而强类型语言用于大型库的众多原因之一。

#7


2  

Rene, please read my answer to "Best Practices for Architecting Large Systems in a Dynamic Language" question here on *. I discuss some benefits of giving away the freedom of dynamic languages to save development effort and to ease introducing new programmers to the project. Interfaces, when used properly, greatly contribute to writing reliable software.

Rene,请在*上阅读我对“动态语言中构建大型系统的最佳实践”问题的回答。我讨论了放弃动态语言*以节省开发工作和简化新程序员引入项目的一些好处。如果使用得当,接口极大地有助于编写可靠的软件。

#8


2  

In a language like PHP where a method call that doesn't exist results in a fatal error and takes the whole application down, then yes interfaces make sense.

在像PHP这样的语言中,不存在的方法调用会导致致命错误并使整个应用程序失效,那么yes接口是有意义的。

In a language like Python where you can catch and handle invalid method calls, it doesn't.

在Python这样的语言中,您可以捕获并处理无效的方法调用,但事实并非如此。

#9


2  

Python 3000 will have Abstract Base Classes. Well worth a read.

Python 3000将具有抽象基类。非常值得一读。

#10


1  

One use of the Java "interface" is to allow strongly-typed mixins in Java. You mix the proper superclass, plus any additional methods implemented to support the interface.

Java“接口”的一个用途是允许Java中的强类型mixin。您可以混合使用适当的超类,以及为支持该接口而实现的任何其他方法。

Python has multiple inheritance, so it doesn't really need the interface contrivance to allow methods from multiple superclasses.

Python具有多重继承,因此它不需要接口设计来允许来自多个超类的方法。

I, however, like some of the benefits of strong typing -- primarily, I'm a fan of early error detection. I try to use an "interface-like" abstract superclass definition.

然而,我喜欢强类型的一些好处 - 主要是,我是早期错误检测的粉丝。我尝试使用“类似接口”的抽象超类定义。

class InterfaceLikeThing( object ):
    def __init__( self, arg ):
        self.attr= None
        self.otherAttr= arg
    def aMethod( self ):
        raise NotImplementedError
    def anotherMethod( self ):
        return NotImplemented

This formalizes the interface -- in a way. It doesn't provide absolute evidence for a subclass matching the expectations. However, if a subclass fails to implement a required method, my unit tests will fail with an obvious NotImplemented return value or NotImplementedError exception.

这在某种程度上正式化了界面。它没有为符合期望的子类提供绝对证据。但是,如果子类未能实现所需的方法,则单元测试将失败,并显示明显的NotImplemented返回值或NotImplementedError异常。

#11


0  

Well, first of all, it's right that Ruby does not have Interface as is, but they have mixin, wich takes somehow the best of both interfaces and abstract classes from other languages.

好吧,首先,Ruby没有接口是正确的,但是他们有mixin,它在某种程度上是两种接口和其他语言抽象类的最佳选择。

The main goal of interface is to ensure that your object SHALL implement ALL the methods present in the interface itself.

接口的主要目标是确保您的对象应该实现接口本身中存在的所有方法。

Of course, interface are never mandatory, even in Java you could imagine to work only with classes and using reflection to call methods when you don't know wich kind of object you're manipulating, but it is error prone and should be discouraged in many ways.

当然,接口永远不是强制性的,即使在Java中,你可以想象只使用类和使用反射来调用方法,当你不知道你正在操作的那种对象时,它很容易出错,应该不鼓励使用很多方法。

#12


0  

Well, it would certainly be easier to check if a given object supported an entire interface, instead of just not crashing when you call the one or two methods you use in the initial method, for instance to add an object to an internal list.

那么,检查给定对象是否支持整个接口肯定会更容易,而不是在调用初始方法中使用的一个或两个方法时不会崩溃,例如将对象添加到内部列表。

Duck typing has some of the benefits of interfaces, that is, easy of use everywhere, but the detection mechanism is still missing.

鸭子打字具有界面的一些好处,即易于使用,但检测机制仍然缺失。

#13


0  

It's like saying you don't need explicit types in a dynamically-typed language. Why don't you make everything a "var" and document their types elsewhere?

这就像说你不需要动态类型语言中的显式类型。为什么不把所有东西都变成“var”并在其他地方记录它们的类型?

It's a restriction imposed on a programmer, by a programmer. It makes it harder for you to shoot yourself in the foot; gives you less room for error.

这是程序员对程序员施加的限制。这让你更难以在脚下射击自己;为您提供更少的错误空间。

#14


0  

as a PHP programmer, the way I see it, an Interface is basically used as a contract. It lets you say that everything which uses this interface MUST implement a given set of functions.

作为一个PHP程序员,我看到它的方式,一个接口基本上用作合同。它可以让你说使用这个接口的一切必须实现一组给定的功能。

I dunno if that's all that useful, but I found it a bit of a stumbling block when trying to understand what Interfaces were all about.

我不知道这是否有用,但我发现在尝试理解接口的全部内容时,它有点绊脚石。

#15


0  

If you felt you had to, you could implement a kind of interface with a function that compares an object's methods/attributes to a given signature. Here's a very basic example:

如果你觉得必须这样做,你可以用一个函数来实现一种接口,该函数将对象的方法/属性与给定的签名进行比较。这是一个非常基本的例子:

file_interface = ('read', 'readline', 'seek')

class InterfaceException(Exception): pass

def implements_interface(obj, interface):
    d = dir(obj)
    for item in interface:
        if item not in d: raise InterfaceException("%s not implemented." % item)
    return True

>>> import StringIO
>>> s = StringIO.StringIO()
>>> implements_interface(s, file_interface)
True
>>> 
>>> fp = open('/tmp/123456.temp', 'a')    
>>> implements_interface(fp, file_interface)
True
>>> fp.close()
>>> 
>>> d = {}
>>> implements_interface(d, file_interface)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 4, in implements_interface
__main__.InterfaceException: read not implemented.

Of course, that doesn't guarantee very much.

当然,这并不能保证很多。

#16


0  

In addition to the other answers I just want to point out that Javascript has an instanceof keyword that will return true if the given instance is anywhere in a given object's prototype chain.

除了其他答案之外,我只想指出Javascript有一个instanceof关键字,如果给定实例在给定对象的原型链中的任何位置,它将返回true。

This means that if you use your "interface object" in the prototype chain for your "implementation objects" (both are just plain objects to JS) then you can use instanceof to determine if it "implements" it. This does not help the enforcement aspect, but it does help in the polymorphism aspect - which is one common use for interfaces.

这意味着如果您在原型链中使用“接口对象”作为“实现对象”(两者都只是JS的普通对象),那么您可以使用instanceof来确定它是否“实现”它。这对执行方面没有帮助,但它确实有助于多态方面 - 这是接口的一个常见用途。

MDN instanceof Reference

MDN instanceof参考

#17


-2  

Stop trying to write Java in a dynamic language.

停止尝试用动态语言编写Java。