为不同的go结构创建构造函数

I have a struct which I initiate in some process like following, and this is working as expected.

This is specific runner

type TestRunner struct {
    path string
    name string
}

func NewRunner(p string, n string) *TestRunner {
    return &TestRunner{
        path: p,
        name: n,
    }
}

Now I want in the same package to create another runner so I do it like this e.g.

Also specific runner

type TestRunner2 struct {
    path string
    name string
}

func NewRunner(p string, n string) *TestRunner2 {
    return &TestRunner2{
        path: p,
        name: n,
    }
}

Now I get error that the func NewRunner is exist

I have another file (in the same package) which include the interface

This is generic implementation (different file in the same package)

type Runner interface {
    Run(path string) error         
    ChangePath(newPath string) 
}

So maybe the NewRunner should be there, where its recommended to put the new object ?

obviously I can create NewRunner1 and NewRunner2 method in the file but im not sure if it’s recommended

First, you should name your runners according to their functionality, not by number. FastRunner and SlowRunner or LocalRunner vs RemoteRunner. You get the idea. Then you should create a construct for each one:

func NewFastRunner( ... ) *FastRunner {
    return &FastRunner{ ... }
}

func NewSlowRunner( ... ) *SlowRunner {
    return &SlowRunner{ ... }
}

This is standard practice, and makes for very readable, unambiguous code.

You can use method pointer type receivers for each runner and then implement interface. That way you need not to return any thing you can directly assign values like path and name to runner using pointer.

package main

import (
    "fmt"
)

type TestRunner1 struct {
    path string
    name string
}

type TestRunner2 struct {
    path string
    name string
}

type Runner interface {
    Run(path string) error
    ChangePath(newPath string)
}

func (tr1 *TestRunner1) NewRunner(p string, n string) {
    tr1.path = p
    tr1.path = n
}

func (tr2 *TestRunner2) NewRunner(p string, n string) {
    tr2.path = p
    tr2.path = n
}

func main() {
    fmt.Println("Hello, playground")
}

Check the code here