Als Material zum Erlernen von GoF-Entwurfsmustern scheint das Buch "Einführung in Entwurfsmuster, die in der erweiterten und überarbeiteten Java-Sprache gelernt wurden" hilfreich zu sein. Da die aufgeführten Beispiele jedoch auf JAVA basieren, habe ich dieselbe Vorgehensweise mit Python versucht, um mein Verständnis zu vertiefen.
Das Iteratormuster ist eines der von GoF (Gang of Four; 4 Banden) definierten Entwurfsmuster. Indem die Mittel zum Auflisten der Elemente des Containerobjekts unabhängig gemacht werden, sollen Iteratoren bereitgestellt werden, die nicht von den internen Spezifikationen des Containers abhängen.
UML class and sequence diagram UML class diagram (Das Obige wird aus Wikipedia zitiert)
Das Iterator-Muster scheint für die Verarbeitung gedacht zu sein, wenn viele Dinge gesammelt werden, in der richtigen Reihenfolge auf sie zeigen und das Ganze scannen. Iterator
wird auf Japanisch manchmal als ** Iterator ** bezeichnet.
Sie werden häufig angezeigt, wenn Sie an der Python-Programmierung beteiligt sind.
Ich möchte tatsächlich ein Beispielprogramm ausführen, das das Iterator-Muster verwendet, und das folgende Verhalten überprüfen.
$ python Main.py
Aroun d the World in 80 days
Bible
Cinderella
Daddy-Long-Legs
Ähnlicher Code wurde in das Git-Repository hochgeladen. https://github.com/ttsubo/study_of_design_pattern/tree/master/Iterator/step1
--Verzeichnisaufbau
.
├── Main.py
└── iterator
├── __init__.py
├── aggregate.py
├── book.py
└── iterator.py
Es ist die Rolle, die die Schnittstelle definiert, die die Elemente der Reihe nach scannt. Im Beispielprogramm übernimmt die Klasse "Iterator" diese Rolle.
iterator/iterator.py
from abc import ABCMeta, abstractmethod
class Iterator(metaclass=ABCMeta):
@abstractmethod
def hasNext(self):
pass
@abstractmethod
def next(self):
pass
Es ist die Rolle, die tatsächlich die Schnittstelle implementiert, die durch die Rolle des "Iterators" definiert ist. Im Beispielprogramm übernimmt die Klasse "BookShelfIterator" diese Rolle. Diese Rolle muss über die zum Scannen erforderlichen Informationen verfügen. Im Beispielprogramm wird die Instanz der Klasse "BookShelf" von der Instanzvariablen "self .__ bookShelf" und das Buch von Interesse von der Instanzvariablen "self .__ index" gespeichert.
iterator/book.py
from iterator.iterator import Iterator
...(snip)
class BookShelfIterator(Iterator):
def __init__(self, bookShelf):
self.__bookShelf = bookShelf
self.__index = 0
def hasNext(self):
return True if self.__index < self.__bookShelf.getLength() else False
def next(self):
book = self.__bookShelf.getBookAt(self.__index)
self.__index += 1
return book
Diese Rolle definiert die Schnittstelle, die die Iterator-Rolle erstellt. Die Schnittstelle ist eine Abstraktionsmethode, die "eine Person erstellt, die die Elemente, die ich in der richtigen Reihenfolge habe, scannt". Im Beispielprogramm übernimmt die Klasse "Aggregat" diese Rolle.
iterator/aggregate.py
from abc import ABCMeta, abstractmethod
class Aggregate(metaclass=ABCMeta):
@abstractmethod
def iterator(self):
pass
Es ist die Rolle, die die durch die Rolle "Aggregat" definierte Schnittstelle tatsächlich implementiert. Erstellen Sie eine konkrete Iterator-Rolle, dh eine Instanz der ConcreteIterator-Rolle. Im Beispielprogramm übernimmt die BookShelf-Klasse diese Rolle.
iterator/book.py
from iterator.aggregate import Aggregate
...(snip)
class BookShelf(Aggregate):
def __init__(self, maxSize):
self.__last = 0
self.__books = [None] * maxSize
def getBookAt(self, index):
return self.__books[index]
def append(self, book):
self.__books[self.__last] = book
self.__last += 1
def getLength(self):
return self.__last
def iterator(self):
return BookShelfIterator(self)
Im Beispielprogramm übernimmt die Methode "startMain" diese Rolle.
Main.py
from iterator.book import Book, BookShelf
def startMain():
bookShelf = BookShelf(4)
bookShelf.append(Book(name="Aroun d the World in 80 days"))
bookShelf.append(Book(name="Bible"))
bookShelf.append(Book(name="Cinderella"))
bookShelf.append(Book(name="Daddy-Long-Legs"))
it = bookShelf.iterator()
while it.hasNext():
book = it.next()
print(book.getName())
if __name__ == '__main__':
startMain()
Buchtitel verwalten.
iterator/book.py
class Book(object):
def __init__(self, name):
self.__name = name
def getName(self):
return self.__name
In der Python-Programmierung sehe ich oft Iteratoren. Informationen zu Python-Iteratoren finden Sie in diesem Webartikel "[Einführung in Python] Was sind Iteratoren?". .. Darüber hinaus müssen beim Definieren einer neuen Klasse die folgenden Anforderungen erfüllt sein, um die Eigenschaften eines Iterators zu haben.
__next__
Methode, die die Werte der Elementspalten zurückgibt, die Sie einzeln verwalten.__next__
wird eine AusnahmeStopIteration
ausgelöst, wenn die Elemente erschöpft sind.Ich möchte das Beispielprogramm mit ** Python Iterator ** umschreiben. Ähnlicher Code wurde in das Git-Repository hochgeladen. https://github.com/ttsubo/study_of_design_pattern/tree/master/Iterator/step2
iterator/book.py
class Book(object):
def __init__(self, name):
self.__name = name
def getName(self):
return self.__name
class BookShelf(object):
def __init__(self):
self.__books = []
def append(self, book):
self.__books.append(book)
def __iter__(self):
self.__index = 0
return self
def __next__(self):
if self.__index >= len(self.__books):
raise StopIteration()
book = self.__books[self.__index]
self.__index += 1
return book
Main.py
from iterator.book import Book, BookShelf
def startMain():
bookShelf = BookShelf()
bookShelf.append(Book(name="Aroun d the World in 80 days"))
bookShelf.append(Book(name="Bible"))
bookShelf.append(Book(name="Cinderella"))
bookShelf.append(Book(name="Daddy-Long-Legs"))
for book in bookShelf:
print(book.getName())
if __name__ == '__main__':
startMain()
Es ist viel einfacher. Lass es uns bewegen.
$ python Main.py
Aroun d the World in 80 days
Bible
Cinderella
Daddy-Long-Legs
Da es sich um das erste Operationsergebnis handelt, ist es vorerst abgeschlossen.
Recommended Posts