The conflict problem of implicit interface in go language

Source: Internet
Author: User

The conflict problem of implicit interface in go language

The go language uses an implicit interface, which can be used as an interface as long as the definition of the interface is satisfied.

such as the built-in error interface:

type error struct {Error() string}

There are many advantages to implicit interfaces. But I personally think that the main point is not to draw the ancestors of the eight Generations of inheritance diagram (loose coupling).

However, an implicit interface can cause conflicting problems.

To put it simply, I also want to define my own MyError interface, which also has a Error() string method:

type MyError struct {Error() string}

But I want MyError interfaces and error interfaces to be of different types (cannot be converted to each other).

Of course, the MyError interface and interface are equivalent in the Go language, and it error is difficult to prohibit the conversion between them.

We can generally MyError add a unique empty method to the interface to avoid this problem:

type MyError struct {Error() stringAssertMyError()}

Method AssertMyError is just to differentiate error the interface, no other use.

This is protobuf in Proto. Message uses the method:

// Message is implemented by generated protocol buffer messages.type Message interface {Reset()String() stringProtoMessage()}

Each type generated Message has a special ProtoMessage null method, which specifically corresponds to the proto.Message interface.

Of course, there is a danger of conflict if there is just another interface that has a ProtoMessage method.

The extreme approach is to randomly generate a special method name, such as a UUID with a unique name.

However, the public name still has the risk of being maliciously covered by others (unlikely in practice).

A more rigorous approach is to define the method name that distinguishes the interface as a private method. For example testing.TB :

type TB interface {Error(args ...interface{})Errorf(format string, args ...interface{})Fail()FailNow()Failed() boolFatal(args ...interface{})Fatalf(format string, args ...interface{})Log(args ...interface{})Logf(format string, args ...interface{})Skip(args ...interface{})SkipNow()Skipf(format string, args ...interface{})Skipped() bool// A private method to prevent users implementing the// interface and so future additions to it will not// violate Go 1 compatibility.private()}

privateIt is not just a private method, but it must be the type of the testing method defined inside the package private() to match this interface!

The testing.TB interface is therefore globally unique and does not present an equivalent, interchangeable interface.

The uniqueness of the interface is now testing.TB guaranteed, but how is this interface implemented externally ( private() testing defined within the package)?

We can testing.TB inherit this method from the interface private() :

package mainimport ("fmt""testing")type TB struct {testing.TB}func (p *TB) Fatal(args ...interface{}) {fmt.Println("TB.Fatal disabled!")}func main() {var tb testing.TB = new(TB)tb.Fatal("Hello, playground")}

Play Address: http://play.golang.org/p/tFB0fLwq9q

The above code simulates an explicit interface, and the testing.TB interface never has to worry about conflicting risks.

Of course, the above code has a problem with overuse techniques, which is contradictory to the simple programming philosophy of Go language.

The conflict problem of implicit interface in go language

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.