Wir können uns OOP als Modellierung des Verhaltens eines Systems vorstellen . Beachten Sie, dass das System nicht in der "realen Welt" existieren muss, obwohl Metaphern in der realen Welt manchmal nützlich sein können (z. B. "Pipelines", "Fabriken" usw.).
Wenn unser gewünschtes System zu kompliziert ist, um es auf einmal zu modellieren, können wir es in kleinere Teile zerlegen und diese (die "Problemdomäne") modellieren, was eine weitere Zerlegung beinhalten kann, und so weiter, bis wir zu Teilen kommen, deren Verhalten übereinstimmt (mehr oder weniger) das eines eingebauten Sprachobjekts wie einer Zahl, einer Zeichenkette, einer Liste usw.
Sobald wir diese einfachen Teile haben, können wir sie kombinieren, um das Verhalten größerer Teile zu beschreiben, die wir zu noch größeren Teilen kombinieren können, und so weiter, bis wir alle Komponenten des Bereichs beschreiben können, die für ein Ganzes benötigt werden System.
In dieser Phase des "Zusammenfügens" könnten wir einige Klassen schreiben. Wir schreiben Klassen, wenn es kein Objekt gibt, das sich so verhält, wie wir es wollen. Beispielsweise könnte unsere Domain "foos", Sammlungen von foos, die als "bars" bezeichnet werden, und Sammlungen von Bars, die als "bazs" bezeichnet werden, enthalten. Wir bemerken vielleicht, dass Foos einfach genug sind, um mit Strings zu modellieren, also machen wir das. Wir stellen fest, dass Balken erfordern, dass ihr Inhalt einer bestimmten Einschränkung entspricht, die nicht mit den von Python bereitgestellten übereinstimmt. In diesem Fall schreiben wir möglicherweise eine neue Klasse, um diese Einschränkung zu erzwingen. Vielleicht haben Bas keine derartigen Besonderheiten, deshalb können wir sie nur mit einer Liste darstellen.
Beachten Sie, dass wir konnten eine neue Klasse für jede dieser Komponenten (Foos, Bars und bazs) schreiben, aber wir nicht brauchen , um , wenn es schon etwas mit dem richtigen Verhalten. Insbesondere, damit eine Klasse nützlich ist, muss sie etwas "bereitstellen" (Daten, Methoden, Konstanten, Unterklassen usw.). Selbst wenn wir viele Ebenen von benutzerdefinierten Klassen haben, müssen wir schließlich ein eingebautes Feature verwenden. Wenn wir beispielsweise eine neue Klasse für foos schreiben würden, würde sie wahrscheinlich nur einen String enthalten. Warum also nicht die foo-Klasse vergessen und die bar-Klasse stattdessen diese Strings enthalten? Denken Sie daran, dass Klassen auch ein integriertes Objekt sind, sie sind nur ein besonders flexibles Objekt.
Sobald wir unser Domänenmodell haben, können wir einige bestimmte Instanzen dieser Teile nehmen und sie in einer "Simulation" des bestimmten Systems anordnen, das wir modellieren möchten (z. B. "ein maschinelles Lernsystem für ...").
Sobald wir diese Simulation haben, können wir sie ausführen und hey presto, wir haben eine funktionierende (Simulation eines) maschinellen Lernsystems für ... (oder was auch immer wir modellieren).
In Ihrer speziellen Situation versuchen Sie nun, das Verhalten einer "Feature Extractor" -Komponente zu modellieren. Die Frage ist, ob es eingebaute Objekte gibt, die sich wie ein "Feature Extractor" verhalten, oder ob Sie es in einfachere Dinge aufteilen müssen. Es sieht so aus, als würden sich Feature-Extraktoren sehr ähnlich wie Funktionsobjekte verhalten. Ich denke, Sie können diese Objekte als Modell verwenden.
Beachten Sie beim Erlernen solcher Konzepte, dass verschiedene Sprachen unterschiedliche integrierte Funktionen und Objekte bereitstellen können (und einige verwenden natürlich nicht einmal eine Terminologie wie "Objekte"!). Daher sind Lösungen, die in einer Sprache sinnvoll sind, in einer anderen möglicherweise weniger nützlich (dies kann sogar für verschiedene Versionen derselben Sprache gelten!).
Historisch gesehen hat sich ein Großteil der OOP-Literatur (insbesondere "Design Patterns") auf Java konzentriert, was sich von Python stark unterscheidet. Beispielsweise sind Java-Klassen keine Objekte, Java hatte bis vor kurzem keine Funktionsobjekte, Java hat eine strenge Typprüfung (die Interfaces und Unterklassen fördert), während Python das Duck-Typing fördert, Java hat keine Modulobjekte, Java-Ganzzahlen / schwimmt / etc. sind keine Objekte, Meta-Programmierung / Introspektion in Java erfordert "Reflektion" und so weiter.
Ich versuche nicht, Java in Betracht zu ziehen (als weiteres Beispiel dreht sich eine Menge der OOP-Theorie um Smalltalk, das sich wiederum sehr von Python unterscheidet), sondern ich möchte nur darauf hinweisen, dass wir sehr sorgfältig über den Kontext und das Thema nachdenken müssen Einschränkungen, in denen Lösungen entwickelt wurden, und ob dies der Situation entspricht, in der wir uns befinden.
In Ihrem Fall scheint ein Funktionsobjekt eine gute Wahl zu sein. Wenn Sie sich fragen, warum in einer "Best Practice" -Richtlinie Funktionsobjekte nicht als mögliche Lösung erwähnt werden, liegt dies möglicherweise einfach daran, dass diese Richtlinien für ältere Versionen von Java geschrieben wurden!