senghoo / golang-design-pattern Goto Github PK
View Code? Open in Web Editor NEW设计模式 Golang实现-《研磨设计模式》读书笔记
License: MIT License
设计模式 Golang实现-《研磨设计模式》读书笔记
License: MIT License
看见写得单例模式中用到了接口(导出的)
注释的是:避免返回一个包私有类型的指针
请教下,返回一个私有类型的指针有什么影响吗,暂时想不出返回私有类型的指针有什么不妥?包本身就是封装并隔离的。
design pattern 21 chain_of_responsibility, implements is not right at all
如下代码验证了空结构体多次赋值结果一样,在单例模式中golang-design-pattern/03_singleton/singleton.go line23,即使不用sync.Once 也能通过单元测试,应该给singleton添加一个字段
`package main
import (
"fmt"
)
var a1 *singleton1
var a2 *singleton2
type singleton1 struct {
}
type singleton2 struct {
d int
}
func getInstance1() *singleton1 {
a1 = &singleton1{}
return a1
}
func getInstance2() *singleton2 {
a2 = &singleton2{}
return a2
}
func main() {
b1, c1 := getInstance1(), getInstance1()
fmt.Println(b1 == c1)
//true
b2, c2 := getInstance2(), getInstance2()
fmt.Println(b2 == c2)
//false
}
`
`
type InterA interface {
DoA()
}
type classA struct{}
func (a classA) DoA() {
fmt.Println("do a thing")
}
func OutDoDo(a InterA) {
a.DoA()
}
// code above is original function. now you want OutDoDO do what classB do, so adapter works
type classB struct{}
func (b classB) DoB() {
fmt.Println("do b thing")
}
type adapter1 struct{}
func (ad adapter1) DoA() {
b := classB{}
b.DoB()
}
// test
func TestAdapterOutDoDo(t *testing.T) {
ad := adapter1{}
OutDoDo(ad)
}
`
观察者模式中,observe.go手误拼错了
作者您好,您这个repo似乎只有《研磨设计模式》中提到的设计模式,我是否能增加一些其他设计模式的go实现并提交pull request呢?还是说在自己的repo中引用您的repo?
Hi,我想 pr
设计模式中部分示例,新的示例有
Readme.md
中说明示例。举一个例子,工厂方法模式。它将存在 IGun.go
\ gun.go
\ ak47.go
\ musket.go
\ gunFactory.go
\ output.txt
\ factorymethod_test.go
🎉 没错,这是一个兵工厂。如果认为不错,那我将开始这个计划,当然!如果您希望维持现状,这也没关系~
golang-design-pattern/10_observer/obserser.go
观察者模式的文件名打错了~
给出的demo代码的确能跑通,但是利用sync.Once.Do()方法实现线程安全的话,会导致整个go进程中只能创建这一种单例
如果我想创建多个用处不同的单例的话,会导致后面的都没法成功
想了两种优化的方案
package singleton
import (
"sync"
)
// Singleton 是单例模式接口,导出的
// 通过该接口可以避免 GetInstance 返回一个包私有类型的指针
type Singleton interface {
foo()
}
// singleton 是单例模式类,包私有的
type singleton struct{}
func (s singleton) foo() {}
var (
instance *singleton
instance2 *singleton2
mu sync.Mutex
)
//GetInstance 用于获取单例模式对象
func GetInstance() Singleton {
mu.Lock()
defer mu.Unlock()
if instance == nil {
instance = &singleton{}
}
return instance
}
type singleton2 struct {
}
func (s2 singleton2) foo() {}
func GetInstance2() Singleton {
mu.Lock()
defer mu.Unlock()
if instance2 == nil {
instance2 = &singleton2{}
}
return instance2
}
package singleton
import (
"sync"
"sync/atomic"
)
// Singleton 是单例模式接口,导出的
// 通过该接口可以避免 GetInstance 返回一个包私有类型的指针
type Singleton2 interface {
foo()
}
// singleton 是单例模式类,包私有的
type singleton21 struct{}
func (s singleton21) foo() {}
var (
instance21 *singleton21
instance22 *singleton22
initInstanceCnt uint32
initInstanceCnt2 uint32
mu sync.Mutex
)
//GetInstance 用于获取单例模式对象
func GetInstance21() Singleton2 {
if atomic.LoadUint32(&initInstanceCnt) == 1 {
return instance21
}
mu.Lock()
defer mu.Unlock()
if initInstanceCnt == 0 {
instance21 = &singleton21{}
atomic.StoreUint32(&initInstanceCnt, 1)
}
return instance21
}
type singleton22 struct {
}
func (s2 singleton22) foo() {}
func GetInstance22() Singleton {
if atomic.LoadUint32(&initInstanceCnt2) == 1 {
return instance22
}
mu.Lock()
defer mu.Unlock()
if initInstanceCnt2 == 0 {
instance22 = &singleton22{}
atomic.StoreUint32(&initInstanceCnt2, 1)
}
return instance22
}
Hi, perhaps this example isn't the best one because there's a potential for type mismatches.
If we want to use type matching here, perhaps 'switch' is a better choice; or at least I think using the following type checking method would be better.
t1, ok := c.(*Type1)
if !ok {
t.Fatal("error")
}
比方说我们已经有了一个fib函数
https://play.golang.org/p/hYerZ2fv0dT
现在我想要在不修改源代码的前提下, 增加一个counter 装饰器
目的是统计fib调用了多少次. 因为里面有递归, 看起来go就解决不了了.
package singleton
import "sync"
//Singleton 是单例模式类
type Singleton struct{}
var singleton *Singleton
var once sync.Once
//GetInstance 用于获取单例模式对象
func GetInstance() *Singleton {
once.Do(func() {
singleton = &Singleton{}
})
return singleton
}
=>
package singleton
import "sync"
//Singleton 是单例模式类
type singleton struct{}
var singleton *singleton
var once sync.Once
//GetInstance 用于获取单例模式对象
func GetInstance() *singleton {
once.Do(func() {
singleton = &singleton{}
})
return singleton
}
//facade implement type apiImpl struct { a AModuleAPI b BModuleAPI }
为什么在这里包含接口而不是struct?
func GetInstance() *Singleton {
if singletonInst == nil {
// 多个线程进入这里会造成死锁
singletonInstLock.Lock()
if singletonInst == nil {
singletonInst = &Singleton{}
}
// 应该在此处UnLock
}
return singletonInst
}
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.