Home > Software design >  How does lower level module and higher level module communicate in golang
How does lower level module and higher level module communicate in golang

Time:09-17

In the following code, I have a lower level module RelationshipBrowser defined a FindAllChildrenOf method and I have a struct Relationships that has the property relations which is a slice and another struct named Research which as the property browser. I declared a receiver function FindAllChildrenOf for Relationships and another receiver function Investigate for Research, I think my question is, when I implement the logics in the function Investigate it's clearly calling the browser interface to trigger the function FindAllChildrenOf and go automatically knows that I am referring to type Relationship. My confusion is, how does RelationshipBrowser and Relationships connect in this context while they seem to have no connection?

const (
    Parent Relationship = iota
    Child
    Sibiling
)

type Person struct {
    name string
}

type Info struct{
    from *Person
    relatiionship Relationship
    to *Person
}

// low-level module
type RelationshipBrowser interface{
    FindAllChildrenOf(name string)[]*Person
    
}

type Relationships struct{
    relations []Info
}

func (r *Relationships)AddParentAndChild(parent,child *Person){
        r.relations = append(r.relations, Info{parent,Parent,child})
        r.relations = append(r.relations, Info{child,Child,parent})
    }

func (r *Relationships)FindAllChildrenOf(name string)[]*Person{
    result:= make([]*Person,0)
    for i,v:= range r.relations{
        if v.relatiionship == Parent && v.from.name==name{
            result = append(result, r.relations[i].to)
        }     
    }
    return result
}
// high-level module



type Research struct{
// break DIP
    // relationships Relationships 
    browser RelationshipBrowser
}

func (r *Research)Investigate(){
    // relations:= r.relationships.relations
    // for _, rel := range relations{
    //  if rel.from.name == "John" && rel.relatiionship == Parent{
    //      fmt.Println("John has a child called", rel.to.name)
    //  }
    // }
        children:=r.browser.FindAllChildrenOf("John")
        for _,child:=range children{
            fmt.Println("John has a child called", child.name)
        }

}

func main(){
    parent:= Person{"John"}
    child1:= Person{"Chris"}
    child2:= Person{"Matt"}
    relationships:= Relationships{}
    relationships.AddParentAndChild(&parent,&child1)
    relationships.AddParentAndChild(&parent,&child2)
    r := Research{&relationships}
    r.Investigate()

}

CodePudding user response:

go automatically knows that I am referring to type Relationship.

Yes, because Go knows the exact address of the RelationshipBrowser, so it can know everything if it want. You can know everything too, through the reflection, see https://go.dev/blog/laws-of-reflection

In your code, you explicitly pass the address here:

r := Research{&relationships}

RelationshipBrowser and Relationships connect together by this address, because Research think of it as a RelationshipBrowser, but it's actually a Relationships.

CodePudding user response:

I just figured out that by calling r.Investigate, the program knows I am referring to the Relationship struct. I am still a go beginner, so the learning curve is deep.

  • Related