Hintergrund
Auf der Wikipedia-Seite zu Syntactic Sugar heißt es:
In der Informatik ist syntaktischer Zucker eine Syntax in einer Programmiersprache, die die Lesbarkeit und Ausdrucksfähigkeit der Dinge verbessern soll. Es macht die Sprache für den Menschen "süßer": Dinge können klarer, prägnanter oder in einem alternativen Stil ausgedrückt werden, den manche bevorzugen.
Ich verstehe nicht wirklich, was der Unterschied zwischen Syntactic Sugar und Syntax ist.
Ich weiß den Punkt zu schätzen, dass die zuckerhaltige Version klarer und prägnanter sein kann und vielleicht ein wenig Dampf aus der Kesselplatte macht. Aber ich bin der Meinung, dass die gesamte Syntax im Wesentlichen darauf abzielt, eine Abstraktion darüber zu bilden, worauf der Code kompiliert wird.
Aus derselben Wikipedia-Seite:
Sprachprozessoren, einschließlich Compiler, statische Analysatoren und dergleichen, erweitern häufig gezuckerte Konstrukte vor der Verarbeitung in grundlegendere Konstrukte, ein Prozess, der manchmal als "Desugaring" bezeichnet wird.
Wenn ich "oft" in dieser Aussage als "immer" bezeichne: Wenn der Unterschied wäre, ob der Compiler die Syntax "desugariert", bevor er zu einer nächsten Stufe übergeht, wie könnte ein Codierer, der die Innereien nicht kennt, dies tun? des Compilers wissen (oder kümmern), was Sugar'd Syntax ist oder nicht?
Eine sehr verwandte Frage auf dieser Seite "Rigorose Definition von syntaktischem Zucker?" hat eine Antwort, die beginnt:
Ich glaube nicht, dass Sie eine Definition für syntaktischen Zucker haben können, da der Ausdruck BS lautet und wahrscheinlich von Leuten verwendet wird, die über "echte Programmierer" sprechen, die "echte Tools" auf "echten Betriebssystemen" verwenden.
Was könnte für mich bedeuten, dass es vielleicht keinen großen Unterschied zum Kodierer gibt, der die Sprache verwendet? Vielleicht ist der Unterschied nur für den Compiler-Schreiber erkennbar? Obwohl es Fälle geben kann, in denen es hilfreich ist, wenn der Programmierer die Sprache verwendet, um zu wissen, was sich unter der Haube des Syntaktischen Zuckers verbirgt. (Aber vielleicht neigt in der Realität ein Diskurs zu diesem Thema dazu, den Begriff als Flammenköder zu verwenden?)
Das Herzstück der Frage
Also ... die kurze Version der Frage:
- Gibt es einen echten Unterschied zwischen Syntax und Syntactic Sugar?
- Wem ist es wichtig?
Extra Denkanstoß
Bonus zum Thema Widerspruch:
Auf der Wikipedia-Seite wird ein Beispiel gegeben:
Zum Beispiel ist in der C-Sprache die
a[i]
Notation syntaktischer Zucker für*(a + i)
Während eine andere Antwort auf die oben verlinkte Frage über das gleiche Beispiel spricht:
Nun überlegen Sie
a[i] == *(a + i)
. Denken Sie an ein C-Programm, das Arrays in irgendeiner Weise inhaltlich verwendet.
Und fasst zusammen, dass:
Die
[]
Notation erleichtert diese Abstraktion. Es ist kein syntaktischer Zucker.
Die gegenteilige Schlussfolgerung für das gleiche Beispiel!
quelle
Antworten:
Der Hauptunterschied besteht darin, dass die Syntax eine Grammatik ist, die in einer Sprache definiert ist, damit Sie einige Funktionen verfügbar machen können. Sobald Sie zu dieser Funktionalität gelangen, wird jede andere Syntax, mit der Sie dasselbe tun können, als Zucker betrachtet. Das führt natürlich zu merkwürdigen Szenarien darüber, welche der beiden Syntaxen der Zucker ist, zumal nicht immer klar ist, welche zuerst kam.
In der Praxis wird syntaktischer Zucker nur zur Beschreibung der einer Sprache hinzugefügten Syntax verwendet, um die Verwendung zu vereinfachen, z. B. zur Erstellung einer Infix-
lhs + rhs
Map fürlhs.Add(rhs)
. Ich würde die Array-Indizierung von C als syntaktischen Zucker betrachten.Dies ist vor allem deshalb wichtig, weil elegante Designs dazu neigen, die Anzahl der Duplikate zu begrenzen. Syntaktischen Zucker zu benötigen (oder zumindest zu wollen), wird von manchen als Zeichen für ein Versagen des Designs angesehen.
quelle
if (a) return blah; ...
Vergleichresult_type res; if (a) res = blah; else {...}; return res;
. Sie müssten bestimmte Sprachen voraussetzen und extrem sprachanwaltlich sein (oft bis hin zur kleinen operativen Semantik), um Unterschiede zwischen diesen Programmen zu finden.Syntax ist das, was ein Sprachprozessor verwendet, um zu verstehen, was die Konstrukte einer Sprache bedeuten. Konstrukte, die als syntaktischer Zucker gelten, müssen ebenfalls vom Sprachprozessor interpretiert werden und sind somit Teil einer Sprachsyntax.
Das, was syntaktischen Zucker vom Rest der Syntax einer Sprache unterscheidet, ist, dass es möglich wäre, den syntaktischen Zucker aus der Sprache zu entfernen, ohne die Programme zu beeinflussen, die in der Sprache geschrieben werden können.
Um eine formalistischere Definition zu geben, würde ich sagen
Dies ist in keiner Weise dazu gedacht, syntaktischen Zucker oder die Sprachen, in denen er vorkommt, zu verunglimpfen, da die Verwendung von syntaktischem Zucker häufig zu Programmen führt, deren Absicht verständlicher ist.
quelle
->
Operator von C, und ich verstehe nicht, dass dieser Operator weniger allgemein ist als alle anderen.Die anderen Antworten haben kein Schlüsselkonzept erwähnt: abstrakte Syntax ; ohne sie macht der Begriff "syntaktischer Zucker" keinen Sinn.
Abstrakte Syntax definiert die Elemente und die Struktur von Sprachen und wie Phrasen dieser Sprache kombiniert werden können, um größere Phrasen zu bilden. Die abstrakte Syntax ist unabhängig von der konkreten Syntax. Der Begriff "syntaktischer Zucker" bezieht sich, wie ich es verstehe, auf die konkrete Syntax.
Im Allgemeinen sollten Sie beim Entwerfen einer Sprache eine konkrete Syntax für jeden Begriff Ihrer abstrakten Syntax erstellen, damit die Benutzer Code in Ihrer Sprache mit einfachem Text schreiben können.
Angenommen, Sie erstellen eine umständliche konkrete Syntax für foo . Die Benutzer beschweren sich und Sie implementieren eine neue konkrete Syntax, um dieselbe abstrakte Syntax darzustellen . Das Ergebnis ist, dass sich Ihre abstrakte Syntax und Semantik nicht geändert haben, Sie jedoch jetzt zwei konkrete Syntaxen für denselben abstrakten Syntaxbegriff haben.
Ich glaube, das ist es, was die Leute meinen, wenn sie "syntaktischen Zucker" sagen - Änderungen, die nur die konkrete Syntax betreffen, aber nicht die abstrakte Syntax oder Semantik.
Und so ist der Unterschied zwischen "syntaktischem Zucker" und "konkreter Syntax" jetzt klar. Mir. :)
Diese Interpretation hilft auch zu erklären, was Alan Perlis gemeint haben könnte, als er sagte: "Syntaktischer Zucker verursacht Krebs des Semikolons": Der gesamte konkrete syntaktische Zucker der Welt kann keine schwache abstrakte Syntax reparieren, und der Aufwand, den Sie für das Hinzufügen dieses Zuckers aufwenden, ist groß Mühe, die Sie nicht mit dem eigentlichen Problem zu tun haben - der abstrakten Syntax.
Ich sollte auch beachten, dass dies nur meine Meinung ist; Ich glaube es nur, weil es die einzige Interpretation ist, an die ich denken kann, die für mich Sinn macht.
quelle
p
auf eine Struktur mit einem Feld gegeben wirdx
, die Ausdrücke(*p).x
undp->x
die gleiche abstrakte Syntax? Aber ich denke, es wäre großartig, wenn alles auf abstrakte oder konkrete Syntax hinauslaufen würde..
an der Wurzel analysiert werden . Der linke Unterknoten der Wurzel ist a*
und sein Kind istp
. Der rechte Unterknoten der Wurzel istx
. Für den zweiten Ausdruck hat der abstrakte Syntaxbaum->
an der Wurzel ein und die Wurzel hat zwei Kinderp
undx
. Ich versuche herauszufinden, ob es sinnvoll ist, beide Ausdrücke unterschiedlich zu analysieren, damit sie den gleichen abstrakten Syntaxbaum haben, aber ich verstehe nicht, wie im Moment.x
(
oder;
), um einen Baum zu erstellen, der die tatsächliche Struktur eines Programms widerspiegelt (siehe en.wikipedia.org/wiki/Abstract_syntax_tree ). In der abstrakten Syntax wird jedoch (noch) nichts über die Semantik des Programms gesagt.Syntaktischer Zucker ist eine Teilmenge der Sprachensyntax. Die Grundidee ist, dass es mehr als eine Möglichkeit gibt, dasselbe zu sagen.
Was es schwierig macht zu sagen, welche Stücke syntaktischer Zucker sind und welche Stücke "reine Syntax", sind Aussagen wie "es ist schwer zu sagen, welche Form zuerst kam" oder "es ist schwer zu wissen, wie der Autor der Sprache es beabsichtigt hat" oder "es ist" etwas willkürlich zu entscheiden, welche Form einfacher ist ".
Was es einfach macht, zu entscheiden, welche Stücke rein oder zuckerhaltig sind, ist die Frage im Rahmen eines bestimmten Compilers oder Interpreten. Die reine Syntax ist das Material, das ein Compiler direkt in Maschinencode konvertiert oder auf das der Interpreter direkt reagiert. Der Zucker ist der Stoff, der zuerst in einen anderen Syntaxstoff umgewandelt wird, bevor diese direkten Dinge passieren. Abhängig von der Implementierung kann dies mit dem, was der Autor beabsichtigt hat, oder sogar mit dem, was die Sprachspezifikation behauptet, identisch sein oder nicht.
In der Praxis wird auf diese Weise die Realität der Sache entschieden.
quelle
Wirklich, Ihr erstes Zitat aus Wikipedia sagt alles "... macht die Dinge leichter zu lesen ...", ".... süßer für den Menschen zu benutzen ....".
In schriftlicher Form können verkürzte Formen wie "nicht" oder "nicht" als syntaktischer Zucker angesehen werden.
quelle
Normalerweise ist Syntaxzucker der Teil der Sprache, der durch einen vorhandenen Teil der Sprache (Syntax) ohne Verlust der Allgemeinheit, aber möglicherweise mit Verlust der Klarheit ausgedrückt werden kann. Manchmal haben die Compiler einen expliziten Desugaring-Schritt, der den vom Quellcode erzeugten AST transformiert und einfache Schritte anwendet, um Knoten zu entfernen, die Zucker entsprechen.
Zum Beispiel hat Haskell Syntaxzucker für Monaden mit folgenden Regeln, die rekursiv angewendet werden
Im Moment spielt es keine Rolle, was es genau bedeutet - Sie können jedoch sehen, dass die spezielle Syntax auf LHS in etwas grundlegenderes auf RHS umgewandelt werden kann (nämlich Funktionsanwendungen, Lambdas und
let
's). Mit diesen Schritten behalten Sie das Beste aus beiden Welten:In ähnlicher Weise können Sie sich in C vorstellen, die Überschreibungsregel zu desugarieren (aufgrund von Überladung des Operators usw. gilt dies nicht für C ++):
Sie können sich vorstellen, alle Programme ohne
->
oder[]
in C zu schreiben , die diese Konstruktion heute verwenden. Es wäre jedoch schwieriger für Programmierer, es zu verwenden, daher lieferte es Syntaxzucker (ich denke, in den 70er Jahren könnte es die Arbeit für Compiler ebenfalls vereinfachen). Es ist möglicherweise weniger klar, da Sie technisch die folgende, vollkommen gültige Regel für das Umschreiben hinzufügen können:Ist Syntaxzucker schlecht? Nicht unbedingt - es besteht die Gefahr, dass es als Frachtkult verwendet wird, ohne eine tiefere Bedeutung zu verstehen. Zum Beispiel sind die folgenden Funktionen in Haskell äquivalent, dennoch würden viele Anfänger die erste Form schreiben, ohne zu verstehen, dass sie Syntaxzucker überbeanspruchen:
Darüber hinaus kann die Syntax sugar die Sprache überkomplizieren oder zu eng sein, um verallgemeinerten Redewendungscode zuzulassen. Es kann auch bedeuten, dass die Sprache nicht mächtig genug ist, um bestimmte Dinge einfach zu erledigen - es kann beabsichtigt sein (geben Sie den Entwicklern keine scharfen Werkzeuge oder eine sehr spezielle Nischensprache, bei der das Hinzufügen eines mächtigeren Konstrukts anderen Zielen schaden würde) oder durch Auslassen - letzteres form gab der syntax sugar den schlechten namen. Wenn die Sprache mächtig genug ist, um andere Konstrukte zu verwenden, ohne Syntaxzucker hinzuzufügen, wird es als eleganter angesehen, diese zu verwenden.
quelle
Ich denke, das offensichtlichste Beispiel wäre die "+ =" - Syntax in C.
und
Machen Sie genau das Gleiche und kompilieren Sie genau den gleichen Satz von Maschinenanweisungen. In der zweiten Form werden einige eingegebene Zeichen gespeichert. Vor allem wird jedoch deutlich, dass Sie einen Wert auf der Grundlage seines aktuellen Werts ändern.
Ich wollte den Post / Prefix-Operator "++" als kanonisches Beispiel anführen, erkannte jedoch, dass dies mehr als syntaktischer Zucker war. Es gibt keine Möglichkeit, den Unterschied zwischen ++ i und i ++ in einem einzelnen Ausdruck mithilfe der
i = i + 1
Syntax auszudrücken .quelle
a[f(x)] += 1
.Zunächst werde ich einige der anderen Antworten mit einem konkreten Beispiel behandeln. Die C ++ 11-bereichsbasierte for-Schleife (ähnlich wie foreach-Schleifen in verschiedenen anderen Sprachen)
ist genau gleichbedeutend mit (dh eine gezuckerte Version von)
Obwohl der Sprache keine neue abstrakte Syntax oder Semantik hinzugefügt wurde, hat sie einen echten Nutzen.
In der ersten Version wird die Absicht (Besuch jedes Elements in einem Container) explizit angegeben. Es verhindert auch ungewöhnliches Verhalten, wie z. B. das Ändern des Containers während des Durchlaufs oder das weitere Vorrücken
iterator
im Schleifenkörper oder das subtile Verwechseln der Schleifenzustände. Dies vermeidet mögliche Fehlerquellen und verringert auf diese Weise die Schwierigkeit, den Code zu lesen und darüber nachzudenken.Zum Beispiel ein Ein-Zeichen-Fehler in der zweiten Version:
gibt einen One-past-the-End-Fehler und ein undefiniertes Verhalten.
Die gezuckerte Version ist gerade deshalb nützlich, weil sie restriktiver ist und daher einfacher zu vertrauen und zu verstehen ist.
Zweitens zur ursprünglichen Frage:
Nein, "syntaktischer Zucker" ist eine (konkrete) Sprachsyntax, die als "Zucker" betrachtet wird, da sie die abstrakte Syntax oder die Kernfunktionalität der Sprache nicht erweitert. Ich mag die Antwort von Matt Fenwick.
Es ist genauso wichtig für die Benutzer der Sprache wie für jede andere Syntax, und darin wird Zucker bereitgestellt, um bestimmte Redewendungen zu unterstützen (und in gewissem Sinne zu segnen).
Zum Schluss noch zur Bonusfrage
Das klingt sehr nach der Definition von syntaktischem Zucker: Es unterstützt (und liefert den Segen der Sprachautoren) die Verwendung von Zeigern als Arrays. Die
p[i]
Form ist nicht wirklich restriktiver als*(p+i)
, der einzige Unterschied ist die klare Mitteilung der Absicht (und ein geringfügiger Gewinn an Lesbarkeit).quelle
Was auch immer die ursprüngliche Konnotation des Ausdrucks war, heutzutage ist es in erster Linie ein abwertender Ausdruck, der fast immer als "nur" oder "nur" syntaktischer Zucker formuliert wird. Es ist so ziemlich nur für Programmierer von Bedeutung, die Dinge auf unleserliche Weise tun und eine präzise Art und Weise wollen, um dies ihren Kollegen gegenüber zu rechtfertigen. Eine Definition von jenen, die den Begriff heute hauptsächlich verwenden, wäre aus ihrer Sicht so etwas wie:
Aus diesem Grund erhalten Sie zwei entgegengesetzte Schlussfolgerungen für dasselbe syntaktische Element. Ihr erstes Beispiel für die Array-Notation ist die Verwendung der ursprünglichen positiven Bedeutung des Begriffs, ähnlich der Antwort von Bart. Ihr zweites Beispiel ist die Verteidigung der Array-Notation gegen die Anschuldigung, syntaktischer Zucker im abwertenden Sinne zu sein. Mit anderen Worten, es wird argumentiert, dass die Syntax eher eine nützliche Abstraktion als eine Krücke ist.
quelle