有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

继承如何将这个Java接口和继承结构转换为Golang?

有没有可能将这种使用接口和继承的Java结构重写为一种惯用的Golang方式

这不是超级复杂的Java代码,但它显示了类继承的优势,但我想尝试在Go中实现同样的结果

Java代码:

首先是一个类接口

public interface WebEntry {
    String perform(ConnectionData connectionData, SessionData sessionData) throws Exception;
}

某个地方有一个网络条目列表WebEntry

List<WebEntry> webEntries = new ArrayList<>();
webEntries.add( new SavePasswordWebEntry() );

一个抽象类UserLoggedInWebEntry,它实现了WebEntry

public abstract class UserLoggedInWebEntry implements WebEntry {

    @Override
    public String perform(ConnectionData connectionData, SessionData sessionData) throws Exception {

        // THIS IS THE LOGIC I DO NOT WANT TO DUPLICATE, HENCE ITS USING CLASS INHERITANCE
        ...

        return userPerform(User user);

    }

    protected abstract String userPerform(User user) throws Exception;

}

通过使用类继承,我们可以创建一个UserLoggedInWebEntry,它的行为仍然是WebEntry,但我们不需要在每次需要“用户登录web条目”实例时复制...逻辑:

public class SavePasswordWebEntry extends UserLoggedInWebEntry {

    @Override
    protected String userPerform(User user) throws Exception {
       ...
    }

}

所以关键是,由于它使用类继承,开发人员只需要实现String userPerform(User user),而不需要在UserLoggedInWebEntry中重复...的逻辑

这在歌朗是否可能实现?如果是这样,情况会是怎样的


共 (2) 个答案

  1. # 1 楼答案

    给你看。我不知道我是否理解正确

    package main
    
    import (
        "fmt"
    )
    
    type ConnectionData struct{}
    type SessionData struct{}
    
    type WebEntry interface {
        Perform(c ConnectionData, s SessionData) (string, error)
    }
    
    type UserLoggedInWebEntry struct {
    }
    
    func (u *UserLoggedInWebEntry) Perform(c ConnectionData, s SessionData) (string, error) {
        return u.UserPerform(c, s)
    }
    
    func (u *UserLoggedInWebEntry) UserPerform(c ConnectionData, s SessionData) (string, error) {
        return "UserLoggedInWebEntry UserPerform", nil
    }
    
    type SavePasswordWebEntry struct {
        UserLoggedInWebEntry
    }
    
    func (sp *SavePasswordWebEntry) Perform(c ConnectionData, s SessionData) (string, error) {
        return "SavePasswordWebEntry Perform", nil
    }
    
    func main() {
        webEntries := make([]WebEntry,0)
        webEntries = append(webEntries, new(SavePasswordWebEntry))
        for _, we := range webEntries {
            fmt.Println(we.Perform(ConnectionData{},SessionData{}))
        }
    }
    

    Playground

  2. # 2 楼答案

    尽管我很喜欢自己得到的“只学一步”的答案,但我还是找到了自己实现同样目标的方法

    可以通过创建一个包装函数userLoggedInWebEntry来解决这个问题,该函数接受WebEntryUserLoggedIn函数签名,但返回WebEntry函数签名

    它实现了与上面的Java继承代码相同的功能,只允许开发人员实现func( user User ) string,并且userLoggedInWebEntry中的逻辑不重复

    https://play.golang.org/p/adrk46YFIl8

    package main
    
    import (
        "fmt"
    )
    
    type ConnectionData string
    type SessionData string
    type User string
    
    type WebEntry func(connectionData ConnectionData, sessionData SessionData) string
    type WebEntryUserLoggedIn func( user User ) string
    
    func main() {
        var webentries []WebEntry
        webentries = append( webentries, userLoggedInWebEntry(SavePasswordWebEntry) )
    
        // Test the invocation
        fmt.Println( webentries[0]("ConnectionData", "SessionData") )
    }
    
    
    func userLoggedInWebEntry( webEntry WebEntryUserLoggedIn ) WebEntry {
    
        return func(connectionData ConnectionData, sessionData SessionData) string {
            // // THIS IS THE LOGIC I DO NOT WANT TO DUPLICATE, HENCE ITS USING CLASS INHERITANCE
            var user User = "John"
            return webEntry( user )
        } 
    
    }
    
    
    func SavePasswordWebEntry( user User ) string {
        return fmt.Sprintf("user is %s", user )
    }