mirror of
https://github.com/crazybber/go-pattern-examples.git
synced 2024-11-26 05:36:03 +03:00
add two iterator patterns examples
This commit is contained in:
parent
6b03c9a4f1
commit
4f6f503260
91
behavior/04_iterator/book_iterator/book_iterator.go
Normal file
91
behavior/04_iterator/book_iterator/book_iterator.go
Normal file
@ -0,0 +1,91 @@
|
|||||||
|
// Package iterator is an example of the Iterator Pattern.
|
||||||
|
package iterator
|
||||||
|
|
||||||
|
// Iterator provides a iterator interface.
|
||||||
|
type Iterator interface {
|
||||||
|
Index() int
|
||||||
|
Value() interface{}
|
||||||
|
Has() bool
|
||||||
|
Next()
|
||||||
|
Prev()
|
||||||
|
Reset()
|
||||||
|
End()
|
||||||
|
}
|
||||||
|
|
||||||
|
// Aggregate provides a collection interface.
|
||||||
|
type Aggregate interface {
|
||||||
|
Iterator() Iterator
|
||||||
|
}
|
||||||
|
|
||||||
|
// BookIterator implements the Iterator interface.
|
||||||
|
type BookIterator struct {
|
||||||
|
shelf *BookShelf
|
||||||
|
index int
|
||||||
|
internal int
|
||||||
|
}
|
||||||
|
|
||||||
|
// Index returns current index
|
||||||
|
func (i *BookIterator) Index() int {
|
||||||
|
return i.index
|
||||||
|
}
|
||||||
|
|
||||||
|
// Value returns current value
|
||||||
|
func (i *BookIterator) Value() interface{} {
|
||||||
|
return i.shelf.Books[i.index]
|
||||||
|
}
|
||||||
|
|
||||||
|
// Has implementation.
|
||||||
|
func (i *BookIterator) Has() bool {
|
||||||
|
if i.internal < 0 || i.internal >= len(i.shelf.Books) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// Next goes to the next item.
|
||||||
|
func (i *BookIterator) Next() {
|
||||||
|
i.internal++
|
||||||
|
if i.Has() {
|
||||||
|
i.index++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Prev goes to the previous item.
|
||||||
|
func (i *BookIterator) Prev() {
|
||||||
|
i.internal--
|
||||||
|
if i.Has() {
|
||||||
|
i.index--
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reset resets iterator.
|
||||||
|
func (i *BookIterator) Reset() {
|
||||||
|
i.index = 0
|
||||||
|
i.internal = 0
|
||||||
|
}
|
||||||
|
|
||||||
|
// End goes to the last item.
|
||||||
|
func (i *BookIterator) End() {
|
||||||
|
i.index = len(i.shelf.Books) - 1
|
||||||
|
i.internal = i.index
|
||||||
|
}
|
||||||
|
|
||||||
|
// BookShelf implements the Aggregate interface.
|
||||||
|
type BookShelf struct {
|
||||||
|
Books []*Book
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iterator creates and returns the iterator over the collection.
|
||||||
|
func (b *BookShelf) Iterator() Iterator {
|
||||||
|
return &BookIterator{shelf: b}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add adds an item to the collection.
|
||||||
|
func (b *BookShelf) Add(book *Book) {
|
||||||
|
b.Books = append(b.Books, book)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Book implements a item of the collection.
|
||||||
|
type Book struct {
|
||||||
|
Name string
|
||||||
|
}
|
22
behavior/04_iterator/book_iterator/book_iterator_test.go
Normal file
22
behavior/04_iterator/book_iterator/book_iterator_test.go
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
// Package iterator is an example of the Iterator Pattern.
|
||||||
|
package iterator
|
||||||
|
|
||||||
|
import "testing"
|
||||||
|
|
||||||
|
func TestIterator(t *testing.T) {
|
||||||
|
|
||||||
|
shelf := new(BookShelf)
|
||||||
|
|
||||||
|
books := []string{"A", "B", "C", "D", "E", "F"}
|
||||||
|
|
||||||
|
for _, book := range books {
|
||||||
|
shelf.Add(&Book{Name: book})
|
||||||
|
}
|
||||||
|
|
||||||
|
for iterator := shelf.Iterator(); iterator.Has(); iterator.Next() {
|
||||||
|
index, value := iterator.Index(), iterator.Value().(*Book)
|
||||||
|
if value.Name != books[index] {
|
||||||
|
t.Errorf("Expect Book.Name to %s, but %s", books[index], value.Name)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
72
behavior/04_iterator/person_iterator/iterator.go
Normal file
72
behavior/04_iterator/person_iterator/iterator.go
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
package iterator
|
||||||
|
|
||||||
|
import "fmt"
|
||||||
|
|
||||||
|
/*
|
||||||
|
设计思想:
|
||||||
|
1. Iterator结构体
|
||||||
|
实现Next() HasNext()方法
|
||||||
|
2. Container容器
|
||||||
|
容器实现添加 移除Visitor 和
|
||||||
|
*/
|
||||||
|
//创建迭代器
|
||||||
|
type Iterator struct {
|
||||||
|
index int
|
||||||
|
Container
|
||||||
|
}
|
||||||
|
|
||||||
|
func (i *Iterator) Next() Visitor {
|
||||||
|
fmt.Println(i.index)
|
||||||
|
visitor := i.list[i.index]
|
||||||
|
i.index += 1
|
||||||
|
return visitor
|
||||||
|
}
|
||||||
|
|
||||||
|
func (i *Iterator) HasNext() bool {
|
||||||
|
if i.index >= len(i.list) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
//创建容器
|
||||||
|
type Container struct {
|
||||||
|
list []Visitor
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Container) Add(visitor Visitor) {
|
||||||
|
c.list = append(c.list, visitor)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Container) Remove(index int) {
|
||||||
|
if index < 0 || index > len(c.list) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
c.list = append(c.list[:index], c.list[index+1:]...)
|
||||||
|
}
|
||||||
|
|
||||||
|
//创建Visitor接口
|
||||||
|
type Visitor interface {
|
||||||
|
Visit()
|
||||||
|
}
|
||||||
|
|
||||||
|
//创建具体的visitor对象
|
||||||
|
type Teacher struct{}
|
||||||
|
|
||||||
|
type Analysis struct{}
|
||||||
|
|
||||||
|
func (t *Teacher) Visit() {
|
||||||
|
fmt.Println("this is teacher visitor")
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a *Analysis) Visit() {
|
||||||
|
fmt.Println("this is analysis visitor")
|
||||||
|
}
|
||||||
|
|
||||||
|
//工厂方法创建迭代器
|
||||||
|
func NewIterator() *Iterator {
|
||||||
|
return &Iterator{
|
||||||
|
index: 0,
|
||||||
|
Container: Container{},
|
||||||
|
}
|
||||||
|
}
|
18
behavior/04_iterator/person_iterator/iterator_test.go
Normal file
18
behavior/04_iterator/person_iterator/iterator_test.go
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
package iterator
|
||||||
|
|
||||||
|
import "testing"
|
||||||
|
|
||||||
|
func TestIterator_Next(t *testing.T) {
|
||||||
|
teacher := new(Teacher)
|
||||||
|
analysis := new(Analysis)
|
||||||
|
//迭代器
|
||||||
|
iterator := NewIterator()
|
||||||
|
iterator.Add(teacher)
|
||||||
|
iterator.Add(analysis)
|
||||||
|
if len(iterator.list) != 2 {
|
||||||
|
t.Error("期望的count is 2")
|
||||||
|
}
|
||||||
|
for iterator.HasNext() {
|
||||||
|
iterator.Next().Visit()
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user