Warum nimmt sum() keine strings?

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
lunar

pillmuncher hat geschrieben:
lunar hat geschrieben:[...]ich glaube, dass man viele Probleme, die man mit Monaden löst, gar nicht hätte, wenn man eine weniger strenge und mehr pragmatische Sprache verwenden würde :)
Ja. Ich habe lange überlegt, welche Monaden man in Python brauchen könnte, und mehr als die Continuation Monade, monadische Parser-Kombinatoren und vielleicht die beschriebene Logging-Monade ist mir nicht eingefallen. Die List-Monade ist durch die list comprehension in Python zur Genüge abgedeckt, die Maybe/Error/Failure-Monaden durch Exceptions, None und Generatoren, die ungültige Werte herausfiltern, die IO-Monade durch print(), input() und open().
In dieser Feststellung versteckt sich ein wesentlicher Kritikpunkt an Monaden: Sie sind eben vor allem ein (mehr oder weniger theoretisches) Konzept zum Entwurf und zur Implementierung von Sprachkonstrukten. Viele übliche Haskell-Monaden bieten Dinge, die in anderen Sprache in der Syntax und Semantik der Sprache selbst integriert sind, wie beispielsweise Ausnahmen oder Zustand.

Durch die Verallgemeinerung solcher Konstrukte in einem theoretischen Konzept und dadurch Verlagerung von der Sprache in die Bibliothek wird die Sprache zwar schlanker und zweifelsohne sehr elegant, aber eben auch schwerer verständlich, weil man eben nicht einfach nur Ausnahmen, Generatoren und IO lernen kann, sondern Monaden verstehen muss, zumindest teilweise auch in der Theorie, um dann all diese Dinge in der Sprache abzubilden zu können.

Darin liegt auch die Hürde für viele Programmierer: DIe Notwendigkeit, ein grundlegendes theoretisches Konzept verstehen zu müssen, anstatt einfach nur die Features eine Sprache lernen zu können.

Letztlich wird Haskell dadurch zu C, wenn auch auf einem ungleich höheren Niveau: Der Sprache fehlen vereinfachende Konstrukte, die bestimmte, häufig benötigte Features zur Verfügung stellen. In C kann man Ausnahmen über goto modellieren, in Haskell über Monaden, doch beides ist letztlich zu kompliziert für Day-to-day-programming.
Benutzeravatar
pillmuncher
User
Beiträge: 1484
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

mutetella hat geschrieben:Ok, ich häng' noch sehr stark an den Begrifflichkeiten fest:

Endofunktion
Sind 'identity', 'add4', 'mul3' und 'pow2' in pillmunchers 'composable'-Beispiel Endofunktionen?
Mir ist noch nicht ganz klar, was damit gemeint ist, dass bei einer Endofunktion
domain -> codomain | input -> output | Definitionsbereich -> Wertebereich
sein muss. Bedeutet das mit anderen Worten, wenn 'int' reinkommt darf auch nur mit 'int' gehandelt werden und muss auch 'int' rauskommen (oder 'str' oder was auch immer)?
Ja, genau. Jede Funktion, die ein oder mehr Argumente von einem bestimmten Typ nimmt, und als Ergebnis einen Wert desselben Typs zurückgibt, ist eine Endofunktion. zB:, sofern x und y Zahlen sind:

Code: Alles auswählen

def f(x):
    return 2 + x
# oder auch:
def g(x, y)
    return 2 + x * 3 + y
In Python kann man das nicht expliziter ausdrücken, weil es dynamisch typisiert ist.

Vorher schrieb ich von Mengen, hier aber von Typen. Für Mathematiker ist das in diesem Kontext dasselbe.
mutetella hat geschrieben:Das Identitätselement...
...ist zur Ermittlung des Typs notwendig? Also letztlich ein type()? Ein Spiegel?
Nein. Vielleicht anders: Das Identitätselement wird häufig auch neutrales Element genannt. Es ist neutral bezüglich der Operation, um die es gerade geht. Wenn die Operation die Addition von ints ist, dann ist das neutrale Element die 0, wei jedes int + 0 wieder es selbst ist. Die 0 verhält sich hier also neutral. Bei der Multiplikation wäre das die 1: zB. 7 * 1 == 7. Für Strings und + ist es der Leerstring, zB. 'hallo' + '' == 'hallo', für Tupel und + ist es (), für Listen und + ist es [] und für Mengen und | ist es set().
mutetella hat geschrieben:Sind das Monoiden...
(0 2 3 -)
('' 'b' 'd' +)
( () (0,) (3,4) *)
... und das keine
(2 3 -)
(0 2 3 /)
( () ('a',) (3,4) *)
??
Nein. Nochmal anders: ein Monoid ist zB. die Menge aller ganzen Zahlen, zusammen mit der Addition und der 0. In der Mathematik schreibt man dann zB.: <Z, +, 0>, das bedeutet "die Menge der ganzen Zahlen, zusammen mit der Operation + und dem Identitätselement 0". Statt Z schreiben wir in Python natürlich int. Ein anderes Monoid wäre <Z, *, 1>, also die ganzen Zahlen zusammen mit der Multiplikation und 1, weil jede Zahl * 1 wieder sie selbst ist. Oder <Str, +, ''>, dh. die Menge aller Strings, zusammen mit der Konkatenationsoperation + und dem Leerstring '', weil jeder String, konkateniert mit '', wieder den ursprünglichen String ergibt. Z und Str sind dabei einfach nur Namen, die man diesen Mengen gibt, so wie Guido den Typen Integer und String die Namen int und str gegeben hat.
In specifications, Murphy's Law supersedes Ohm's.
mutetella
User
Beiträge: 1695
Registriert: Donnerstag 5. März 2009, 17:10
Kontaktdaten:

@pillmuncher
Ok, was das Identitätselement (neutrales Element finde ich eigentlich passender) ist, hab' ich somit (wahrscheinlich) kapiert. Nur:
  • Wenn nicht zur Typisierung (Identität?), für was braucht es das dann?
  • Und wie wird ein Monoid dann typisiert?
  • Oder ist ein Monoid selbst ein Typ?
pillmuncher hat geschrieben:... und für Mengen und | ist es set().
Was bedeutet hier das | ?

Zu Deinem 'compose'-Beispiel:
Wenn ich Dich richtig verstanden habe, dann sind die Endofunktionen 'add4', 'mul3' und 'pow2' Moniden und

Code: Alles auswählen

compose(add4, mul3)
gibt einen Monaden zurück.
Wenn dem so ist, welche Rolle spielt dabei die 'identity'... eigentlich dieselbe Frage wie schon oben...?

mutetella
Entspanne dich und wisse, dass es Zeit für alles gibt. (YogiTea Teebeutel Weisheit ;-) )
derdon
User
Beiträge: 1316
Registriert: Freitag 24. Oktober 2008, 14:32

Das bedeutet das |, also Vereinigung (engl. union):

Code: Alles auswählen

>>> a = {1, 2, 3}
>>> b = {3, 4, 5}
>>> a | b
set([1, 2, 3, 4, 5])
Benutzeravatar
pillmuncher
User
Beiträge: 1484
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

@mutetella: Ich glaube, ich habe dich mit zu vielen unterschiedlichen Konzepten auf einmal zugeschüttet, ohne wirklich zu erklären, wie eines auf dem anderen aufbaut, und was unten und was oben ist. Ich versuche es nochmal anders und fange ganz von vorne an, wobei ich der Vollständigkeit halber auch Sachen beschreiben werde, die du schon kennst.

Beim Lesen solltest du immer im Hinterkopf behalten, was John v. Neumann einem Studenten sagte, der sich beklagte, weil er etwas nicht verstand: "Junger Mann, man versteht die Sachen in der Mathematik nicht, man gewöhnt sich nur an sie". Tatsächlich ist das u.s. bloß der Aufbau einer Struktur aus Begriffen bzw. Konzepten, mit denen man über mathematische Gegenstände sprechen kann, aber keine komplizierten Formeln oder Berechnungen.


Die angesprochen Konzepte stammen aus der abstrakten Algebra. Der typische Mathematikunterricht in der Schule benutzt zwar deren Konzepte, aber nur zur Darstellung im Rahmen dessen, was er tatsächlich ist: Rechenunterricht. Abstrakte Algebra beschreibt die Strukturen, innerhalb derer man rechnen kann, und zwar auf so allgemeine Weise, dass es den Schulunterricht sprengen würde. Man kann zB. eine Algebra für reguläre Ausdrücke angeben, und völlig zu Recht das Zerlegen von Strings mittels regulärer Ausdrücke "Rechnen" nennen. Im Englischen ist das viel offensichtlicher, denn das englische Wort für Rechnen ist Computing. Das ist das, was Programmierer ihre "Rechner" tun lassen. Die Konzepte der abstrakten Algebra gehören deswegen zum Fundament der theoretischen Informatik, und alle anderen Bereiche wie Zahlentheorie, Berechenbarkeitstheorie, Automatentheorie usw. lassen sich algebraisch darstellen.


Das grundlegendste Konzept ist das der Menge. Eine Menge ist eine ungeordnete Ansammlung von beliebig vielen "Dingen", wobei jedes einzelne Ding höchstens einmal in einer Menge vorkommt. Sie werden durch Aufzählung in geschweiften Klammern dargestellt, zB. {Adam, Eva}, {Tick, Trick, Track}, {2, 3, 5, 7}. Ungeordnet bedeutet einfach, dass die Reihenfolge der Aufzählung keine Rolle spielt. Die Menge {Adam, Eva} ist dieselbe, wie die Menge {Eva, Adam}.

Mengen kann man Namen geben, zB. Z, die Menge aller ganzen Zahlen, oder Q, die Menge aller rationalen Zahlen, oder Str, die Menge aller Strings, usw.

Die Dinge in einer Menge nennt man Elemente. Wenn ein Element x in einer Menge M enthalten ist, dann schreibt man oft auch kurz: "x ist in M", oder "x in M".

Man kann Mengen auch durch die sog. Komprehension darstellen: {x | x in Z, x > 5}, d.i. alle ganzen Zahlen größer als 5, oder {x | x war mit Henry VIII. verheiratet}, was dieselbe Menge ist wie {Katharina von Aragón, Anne Boleyn, Jane Seymour, Anna von Kleve, Catherine Howard, Catherine Parr}, oder {(x, y) | x in Z, y in Str} was bedeutet: die Menge aller geordneten Paare mit einer ganzen Zahl an erster und einem String an zweiter Stelle: (1, 'Brezel'), (7, 'sieben'), (123, 'Garmisch-Partenkirchen'), ... Die Komprehension sollte einem Pythonista bekannt vorkommen, wg. List Comprehensions, und ab Python 2.7 gibt es sogar Set Comprehensions: {x for x in some_numbers if x > 5}. Das ist praktisch eine 1:1-Übersetzung des ersten Beispiels.

Das | spricht man gewöhnlich aus als "wobei" oder "so dass". Es wird weiter unten in anderem Kontext wieder auftauchen.


Das nächste Konzept ist das der Funktion. Eine Funktion ist eine eindeutige Zuordnung zwischen den Elementen von Mengen. Angenommen die Mengen S={1, 2, 3, 4} und T={2, 4, 6, 8}, dann kann man zB. folgende Zuordnung wählen:

Code: Alles auswählen

S --> T:
1 --> 2
2 --> 4
3 --> 6
4 --> 8
Man könnte auch statt dieser Tabelle eine Rechenregel verwenden:

Code: Alles auswählen

f x: x * 2 | 1 <= x <= 4
Oder in Python-Syntax:

Code: Alles auswählen

def f(x):
    if 1 <= x <= 4:
        return x * 2
    else:
        raise ValueError('f is not defined for values smaller than 1 or greater than 4!')
Der wichtige Punkt ist, dass die Funktion, mathematisch gesehen, durch die Mengen und die Zuordnung zwischen den Elementen schon vollständig definiert ist.

Eindeutig bedeutet, dass jedem Wert der ersten Menge genau ein Wert der zweiten Menge zugeordnet wird. zB. kann die Anzahl der Kilometer des kürzesten Weges zwischen Köln und x nicht zwei oder mehr Zahlen sein, da entweder beide Wege gleich lang sind und deswegen dieselbe Anzahl an Kilometern besitzen, oder einer von beiden kürzer ist, so dass dieser auch eine geringere Anzahl von Kilometern hat, wodurch der andere eben kein kürzester Weg mehr wäre.

Es könnte jedoch zwei Orte A und B geben, die gleich weit von Köln entfernt sind. Dann wäre die Anzahl der Kilometer des kürzesten Weges von Köln nach A dieselbe, wie die von Köln nach B. Die Funktion wäre dann immer noch eindeutig, weil dafür ja nur gefordert wird, dass es keine zwei unterschiedlich langen kürzesten Wege gibt, die beide von Köln nach A, oder beide von Köln nach B gehen.

Eine andere Funktion wäre zB. g x: y | y ist mit x verheiratet. Wenn Anton mit Emily, Bernd mit Franziska und Christian mit Dorothea verheiratet ist, dann könnte man das in Python so formulieren:

Code: Alles auswählen

married_with = {
    'Anton': 'Emily',
    'Bernd': 'Franziska',
    'Christian': 'Dorothea'
}
g = married_with.__getitem__
assert g('Bernd') == 'Franziska'
Man würde wohl einen besseren Namen als g verwenden, zB. wife_of, aber mathematisch gesehen wäre es immer noch dieselbe Funktion, weil zwei Funktionen genau dann gleich sind, wenn sie dieselben Zuordnungen vornehmen. Diese Zuordnungen lassen sich auch als Wertepaare darstellen, zB. in Pyhon:

Code: Alles auswählen

assert set((('Anton', 'Emily'), ('Bernd', 'Franziska'), ('Christian', 'Dorothea'))) == set(married_with.items())
Die Definitionsmenge (engl. Domain) einer Funktion ist die Menge der ersten Elemente der Wertepaare, die Wertemenge (engl. Codomain) ist die Menge zweiten Elemente. In Python:

Code: Alles auswählen

domain = set([x for x, y in married_with.items()])
codomain = set([y for x, y in married_with.items()])
#oder:
domain = set(married_with.keys())
codomain = set(married_with.values())
assert domain == set(('Anton', 'Bernd', 'Christian'))
assert codomain == set(('Dorothea', 'Emily', 'Franziska'))
Funktionen können auch mehr als ein Argument haben, zB. f(x, y): der Abstand zwischen x und y, oder g(a, b, c): das Dreieck mit den Koordinaten a, b und c, oder h(n, x): die in höchstens n Schritten erreichbaren Straßen von da aus gezählt, wo x wohnt.

Funktionen besitzen eine sog. Signatur. Das ist ein Ausdruck, der beschreibt, welche Mengen bei der Zuordnung involviert sind. zB. hat eine Funktion, die eine ganze Zahl einer anderen zuordnet, wie f x: x * 2, die Signatur Z --> Z. Die Funktion wife_of oben hat die Signatur Man --> Woman, oder Husband --> Wife. Die Funktion mit den Dreieckskoordinaten oben hätte die Signatur Coor x Coor x Coor --> Triangle, wobei Coor die Menge der Koordinaten, Triangle die Menge der Dreiecke und x das Kreuzprodukt ist.

Endofunktionen sind Funktionen, bei denen alle Argumente und auch der Wert, der ihnen durch die Funktion zugeordnet wird, Elemente derselben Menge sind. Ihre Signatur ist dann T^n --> T für die Menge T über der sie Endofunktionen sind. Das caret soll "hoch" heißen, wie in 3² == 9. T³ --> T ist dann dasselbe wie T x T x T --> T.

Man sagt übrigens meist "für ... nimmt die Funktion den Wert --- an" oder "... wird abgebildet auf ---" statt "... wird --- zugeordnet".


Das nächte Konzept ist das einer Algebra. Das ist eine Struktur mit bestimmten Eigenschaften. Sie besteht aus einer Menge M von Elementen (Zahlen, Strings, ...) und wenigstens einer 2-stelligen Operation. Operation ist in diesem Kontext nur ein anderes Wort für Endofunktion. Diese erzeugt also aus je zwei Elementen der Menge wieder ein drittes derselben, dh. sie hat die Signatur M² --> M. zB:

Code: Alles auswählen

3 + 4 == 7
2 * 5 == 10
'hallo' + 'welt' == 'hallowelt'
[1, 2] + [3, 4] == [1, 2, 3, 4]
set([1, 2, 3]) | set([3, 4, 5]) == set([1, 2, 3, 4, 5])
Diese Beispiele sollen im Speziellen etwas verdeutlichen, was im Allgemeinen gilt. Eine Algebra besteht nicht aus genau den Zahlen 3 und 4 und der Addition, oder den Strings 'hallo' und 'welt' und der Konkatenation, sondern aus allen ganzen Zahlen mit der Addition und allen Strings mit der Konkatenation. Die konkreten Beispiele sollen nur das allgemeine Schema anhand eines Einzelfalles illustrieren.


Eine Algebra stellt man üblicherweise durch Aufzählung in spitzen Klammern dar. Erst kommt die Menge der Elemente, um die es geht, die sog. Trägermenge, und danach Operationen und Konstanten: <M, op1, op2, ..., k1, k2, ...>. Diese Form der Darstellung nennt man die Signatur einer Algebra.


Die einfachste Form einer Algebra nennt man Magma: zB. <Z, ->, das sind die ganzen Zahlen zusammen mit der Subtraktion, oder <Q\0, />, das sind die Rationalen Zahlen ohne 0 zusammen mit der Division.


Ein Magma, dessen Operation assoziativ ist, nennt man Halbgruppe. Angenommen eine Menge M und eine Operation ° über deren Elementen, also eine Algebra mit der Signatur <M, °>. Dann bedeutet "assoziativ", dass für alle Elemente a, b und c in M gilt, dass (a ° b) ° c == a ° (b ° c) ist. Für die Algebren aus dem letzten Absatz gilt das offensichtlich nicht, da zB. (7 - 5) - 2 != 7 - (5 - 2) und (12.4 / 3.1) / 2.0 != 12.4 / (3.1 / 2.0) ist. Ein Beispiel für eine Halbgruppe wäre die Menge aller nicht-leeren Strings NLStr und die Konkatenation +: <NLStr, +>, weil die Konkatenation assoziativ ist:

Code: Alles auswählen

('ich' + 'mach') + 'brotzeit' == 'ich' + ('mach' + 'brotzeit')
       'ichmach' + 'brotzeit' == 'ich' + 'machbrotzeit'
            'ichmachbrotzeit' == 'ichmachbrotzeit'
Wenn die Trägermenge einer Halbgruppe ein Identitätselement bezüglich der Operation enthält, dann erhält man ein Monoid. Das Identitätselement ist das Element der Trägermenge, dass sich in Bezug auf die Operation neutral verhält. Die allgemeine Signatur hat dann die Form <M, °, I>, wobei M die Trägermenge, ° die Operation und I das Identitätselement ist. Beispielsweise <N, +, 0>, d.i. die Menge der natürlichen Zahlen, zusammen mit der Addition und der 0, oder <N\0, *, 1>, also die natürlichen Zahlen ohne 0 zusammen mit der Multiplikation und der 1, oder <Str, +, ''>, d.h. Strings zusammen mit der Konkatenation und dem Leerstring. Oder, sofern 1-Endo-T die Menge der 1-stelligen Endofunktionen über der Menge T, * die Funktionskomposition und identity(x): x | x in T die Identitätsfunktion ist, <1-Endo-T, *, identity>. Das war das Beispiel aus meinem anderen Artikel, wo ich einen Decorator zur Funktionskomposition gezeigt hatte. Funktionskomposition hört sich kompliziert an, ist aber tatsächlich sehr einfach. Wenn man lauter 1-stellige Endofunktionen hat, dann kann man entweder so rechnen:

Code: Alles auswählen

x = f(a)
y = g(x)
z = h(y)
Oder einfacher:

Code: Alles auswählen

z = h(g(f(a)))
Bei der Funktionskomposition "kettet" nun man einfach Funktionen aneinander:

Code: Alles auswählen

u = f * g * h
z = u(a)
f * g * h bedeutet also einfach: wende erst f auf einen Wert an, wende auf dessen Ergebnis g an und auf dessen Ergebnis wiederum h. Das funktioniert, weil die Werte, die jede dieser Funktionen annehmen kann, alles Elemente derselben Menge sind. Generell kann man zwei Funktionen komponieren, wenn die Wertemenge der ersten Funktion gleich der Definitionsmenge der zweiten ist, zB. in Python chr und str.lower, das erste wandelt eine Zahl in einen String um, und das zweite einen String in Kleinbuchstaben, also wieder einen String. zB. chr(70) == 'F' und str.lower('F') == 'f'. Also ist (chr * str.lower)(70) == 'f'.


Was aber, wenn das nicht der Fall ist? Wenn man zB. eine Menge von Funktionen hat, die alle dieselben Definitions- und Wertemengen haben, aber diese nicht kompatibel zueinander sind? Also zB. wenn alle die Signatur Z --> (Z, Str) haben, dh. wenn jede dieser Funktionen eine ganze Zahl auf eine ganze Zahl und einen String abbildet? Kann man dann etwas der Funktionskomposition vergleichbares trotzdem konstruieren?


Das bringt uns zum nachsten Konzept, der Monade. Diese stammt nicht aus der abstrakten Algebra, sondern aus der Kategorientheorie, auf die ich nicht weiter eingehen werde, weil ich selber gerade erst angefangen habe, das zu lernen.

Tatsächlich möchte ich hier auch die Monaden nicht nochmal erklären, weil es schon spät ist. Sobald dir die hier beschriebenen Konzepte klar sind, wirst du auch die Erklärung der Monaden aus meinem vorhergehenden Posting verstehen.

Ich möchte nur noch erwähnen, dass es in der abstrakten Algebra noch weitere Arten von Strukturen gibt. Für Informatiker interessant sind zB. Verbände und Scott-Domains. Letztere verwendet man, um die Semantik von Programmiersprachen zu beschreiben. Für's tägliche Programmiergeschäft braucht man sie aber nicht.
In specifications, Murphy's Law supersedes Ohm's.
Benutzeravatar
kbr
User
Beiträge: 1487
Registriert: Mittwoch 15. Oktober 2008, 09:27

@pillmuncher: welch ein Einsatz - Chapeau!
Benutzeravatar
snafu
User
Beiträge: 6740
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

Ich frage mich ehrlich gesagt auch, was es bringen soll, einen Informatik-Laien dermaßen mit eng aneinander gereihten Fachbegriffen zuzuballern. Ein paar Links, wo die verschiedenen Themen in didaktisch angemessenem Tempo erläutert werden, wäre an dieser Stelle vermutlich hilfreicher gewesen, als mehr oder weniger den Inhalt einer Vorlesung über theoretische Informatik (oder zumindest Teile davon) und vielleicht noch ein paar Konzepte aus der Logik in einen einzigen Forenbeitrag zu komprimieren. Nichts für ungut.
Benutzeravatar
pillmuncher
User
Beiträge: 1484
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

@snafu: Ein Grund für die Länge des Postings war, das mutetella bei ein paar Sachen nachgefragt hatte, und da wollte ich nicht einfach ein paar Links hinknallen und sagen "lass mich in Ruhe und lies das". Statt dessen habe versucht, an ein paar Stellen, wo ich den Eindruck hatte, mutetella sei völlig auf dem Holzweg, möglichst klar darzustellen, wie es tatsächlich funktioniert. An anderen Stellen habe ich absichtlich etwas vereinfacht und Sachen ein wenig ungenau dargestellt, weil es IMO an diesen Stellen mehr auf das Grundsätzliche ankam.

Desweiteren bin ich natürlich kein Didaktiker. Ich weiß nicht, wie Menschen am einfachsten abstrakte Algebra lernen. Ich habe es halt so organisiert, dass die jeweils neuen Konzepte auf den vorherigen aufbauen. Da ich nicht wusste, welche Grundlagen bei mutetella vorhanden sind, musste ich bei Adam und Eva, dh. bei Mengen und Funktionen anfangen. Dadurch wurde es natürlich nochmal länger.

An ein paar Stellen habe ich versucht, Querverweise auf Python unterzubringen, weil mutetella Python ja schon kennt und es dadurch vielleicht einfacher verständlich ist.

Ich habe jedes Thema in einzelnen Absätzen dargestellt, damit es bei evtl. Nachfragen einfach zu zitieren ist. Außerdem habe ich die wichtigen Begriffe kursiv gesetzt, damit man gleich sehen kann, was man googeln sollte.

Ich hatte auch erst daran gedacht, ein paar Links zu posten, ich wusste aber nicht, welche. Die Wikipedia-Artikel sind für Anfänger IMO ungeeignet, weil sie zuviel Vorwissen voraussetzen und viel zu detailliert sind, und weil sie die Themen nicht linear als Mengen -> Funktionen -> Algebren präsentieren, sondern jedes Thema für sich mit Querverweisen auf viele andere Themen, die oft für das grundlegende Verständnis völlig irrelevant und viel zu fortgeschritten sind. Wie soll sich ein Anfänger da zurechtfinden?

Andere Quellen kenne ich leider nicht. Ich habe versucht, auf youtube etwas zu finden, aber ohne Erfolg. Über Monoide habe ich nur sehr kategorientheoretische Sachen gefunden, und das meist auf Englisch. Auf Deutsch gibt es nur einiges über Grupppen. Mathematiker interessieren sich anscheinend nicht wirklich für Halbgruppen und Monoide, und lieben statt dessen Gruppen. Wahrscheinlich, weil man Gruppen in der Physik verwendet. In der Informatik trift man aber viel öfter auf einfachere Strukturen, wie eben Monoide. Es gibt keinen String oder Arrayindex, der invers zu einem anderen ist.

Vielleicht sollte ich mal recherchieren und ein paar Links über theoretische Informatik etc. zusammentragen. Die könnte man dann in ein sticky Posting oder eine Wikiseite packen, falls das überhaupt zum Thema Python passt.


@mutetella: Wenn etwas unklar ist, frag mich.
In specifications, Murphy's Law supersedes Ohm's.
mutetella
User
Beiträge: 1695
Registriert: Donnerstag 5. März 2009, 17:10
Kontaktdaten:

pillmuncher hat geschrieben:Die Wikipedia-Artikel sind für Anfänger IMO ungeeignet, weil sie zuviel Vorwissen voraussetzen und viel zu detailliert sind, ... [...] @mutetella: Wenn etwas unklar ist, frag mich.
Genau so geht es mir... Von daher vielen Dank für Deine große Mühe, mir helfen Deine Ausführungen sehr weiter!! Und ja, ich bin so frei und frag' nach, wenn ich fest stecke!
snafu hat geschrieben:... was es bringen soll, einen Informatik-Laien dermaßen mit eng aneinander gereihten Fachbegriffen zuzuballern.
Dazu möchte ich sagen, dass ich während diesem Thread zum Ausdruck brachte, dass mich das Thema Monoiden/Monaden durchaus interessiert und ich als Informatik-Laie zwar schwer daran zu kauen habe aber das auch in Kauf nehme.
Was es bringen soll? Dazu kann ich nur sagen, dass es noch nicht so lange her ist, da ich die Unterschiede zwischen list und tuple nachschlagen musste und Zusammenhänge, die mir heute durchaus klar sind nicht sehen und verstehen konnte. Hätte ich nicht immer und immer wieder die Antworten und Codebeispiele gerade auch in diesem Forum durchgekaut, hätte ich doch niemals etwas dazugelernt, oder?
Wenngleich ich Deines und das Niveau vieler hier nie mehr erreichen werde bin ich an sehr vielem, was hier gefragt und geantwortet wird äußerst interessiert. Ich möchte nicht Laie bleiben, auch wenn mir natürlich klar ist, dass ich es wie jeder andere auch in fast allen Bereichen bleiben werde.
snafu hat geschrieben:Nichts für ungut.
Auf keinen Fall... :)

mutetella
Entspanne dich und wisse, dass es Zeit für alles gibt. (YogiTea Teebeutel Weisheit ;-) )
Antworten