types that implement an interface, in a place where I'm using the interface
as a type to group them together. I've cut my program down to demonstrate
the effect, and explained it inline in the code (also available at
http://play.golang.org/p/_TGARDvBSF ). The nearest post I can find in the
archives is
https://groups.google.com/forum/#!searchin/golang-nuts/convert$20function$20interface/golang-nuts/awwdsmqTRNA/LkOMmxjsHakJ
but I don't think it's quite the same problem. For the problem
description, look for "If I uncomment these" in the code below:
// Program demonstrating a problem I'm having with trying to cast /
// convert functions returning various types that implement an
// interface, to a type that specifies that interface
package main
import "fmt"
// real job dispatch
type SshJob struct {
host string
command string
}
func BuildSshJob(host, command string) SshJob {
return SshJob {
host: host,
command: command,
}
}
func (j SshJob)StartJob() {
fmt.Printf("Starting job \"%s\" on %s via SSH\n", j.command, j.host)
}
// dummy job dispatch
type DummyJob struct {
host string
command string
}
func BuildDummyJob(host, command string) DummyJob {
return DummyJob {
host: host,
command: command,
}
}
func (j DummyJob)StartJob() {
fmt.Printf("Pretending to start job \"%s\" on %s\n", j.command, j.host)
}
// Common interface to real and dummy jobs
type UnderlyingJob interface {
StartJob()
}
type UnderlyingJobCreatorFunc func(host string, command string)
UnderlyingJob
// some wrappers, because I can't get it to work without them
func BuildSshJob_wrapper(host, command string) UnderlyingJob {
return BuildSshJob(host, command)
}
func BuildDummyJob_wrapper (host, command string) UnderlyingJob {
return BuildDummyJob(host, command)
}
// map from type name to function to create appropriate structure
var UnderlyingJobCreators = map[string]UnderlyingJobCreatorFunc {
// A work-round, but not what I really wanted:
"wrapped_dummy": BuildDummyJob_wrapper,
"wrapped_real": BuildSshJob_wrapper,
// These two are how I really wanted to do this, but they
// won't compile; I can create wrapper functions which do the
// conversion dynamically, but the language doesn't let me do
// the conversion statically here.
// If I uncomment these, I get:
// ./fif.go:81: cannot convert BuildDummyJob (type func(string, string)
DummyJob) to type UnderlyingJobCreatorFunc
// ./fif.go:82: cannot convert BuildSshJob (type func(string, string)
SshJob) to type UnderlyingJobCreatorFunc
// "dummy": UnderlyingJobCreatorFunc(BuildDummyJob),
// "real": UnderlyingJobCreatorFunc(BuildSshJob),
}
func BuildUnderlyingJob(jobtype string, host string, command string)
UnderlyingJob {
return UnderlyingJobCreators[jobtype](host, command)
}
// program using either type of job
func main() {
fmt.Println("hello")
dryrunner_0 := BuildDummyJob("localhost", "echo Hello Dummy")
dryrunner_0.StartJob()
runner_0 := BuildSshJob("localhost", "echo Hello network")
runner_0.StartJob()
dryrunner_1 := BuildUnderlyingJob("wrapped_dummy", "localhost", "echo
Hello Dummy")
dryrunner_1.StartJob()
runner_1 := BuildUnderlyingJob("wrapped_real", "localhost", "echo Hello
network")
runner_1.StartJob()
}
I'm new to Go (my background is Lisp, C, and Python), but I've asked
colleagues who're more experienced in Go, and they reckon this should be
possible, but they can't see how, either.
__John
--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.