Parser - Unäres und Binäres Minus

Fragen zu allen anderen Programmiersprachen.
Benutzeravatar
STARGÅTE
Kommando SG1
Beiträge: 6996
Registriert: 01.11.2005 13:34
Wohnort: Glienicke
Kontaktdaten:

Parser - Unäres und Binäres Minus

Beitrag von STARGÅTE »

Hallo Leute,

eh ich mir weiter 'n Wolf suche will ich mein "Problem" einmal mal hier aufzeigen.
Ich suche nach einer passenden Grammatik, die sowohl das unäre Minus als auch das binäre Minus versteht, ohne dass ich das unäre Minus klammern muss. Dabei soll das unäre Minus aber auf keinen Fall eine höhere Priorität haben als zB ein Malzeichen, zwar führt (-x)*y bei der Multiplikation zum gleichen Ergebnis wie -(x*y) aber das ist nicht immer der Fall.
Somit soll es die gleiche Priorität haben wie ein binäres Minus.

Wie müsste meine Grammatik erweitert werden (Startsymbol S)?
S -> E
E -> '-' E ; Möglich, aber dann kann x*-y nicht interpretiert werden, sondern nur x*(-y)
E -> E '+' T
E -> T
T -> T '*' F
T -> F
F -> '(' E ')'
F -> '-' F ; Nicht möglich, da sonst zu hohe Prio und -x*y wird als (-x)*y interpretiert
F -> var
Akzeptiert werden soll zB:
x * -y als x * (-y)
x * -y * z als x * (-y) * z
- x * y als -(x*y)
x - - y als x-(-x)
PB 6.01 ― Win 10, 21H2 ― Ryzen 9 3900X, 32 GB ― NVIDIA GeForce RTX 3080 ― Vivaldi 6.0 ― www.unionbytes.de
Aktuelles Projekt: Lizard - Skriptsprache für symbolische Berechnungen und mehr
Benutzeravatar
NicTheQuick
Ein Admin
Beiträge: 8675
Registriert: 29.08.2004 20:20
Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti
Wohnort: Saarbrücken
Kontaktdaten:

Re: Parser - Unäres und Binäres Minus

Beitrag von NicTheQuick »

Sorry, bin nur grad am Handy, aber hab das hier gefunden: https://stackoverflow.com/a/10556521
Bild
Benutzeravatar
Josh
Beiträge: 1028
Registriert: 04.08.2009 17:24

Re: Parser - Unäres und Binäres Minus

Beitrag von Josh »

Entweder bin ich jetzt komplett falsch dran oder du siehst ein Problem wo keines ist.

Ein unary Minus hat in jeden Fall höchste Priorität. Wenn du ein Literal hast, ist das unary Minus ja quasi ein Bestandteil des Literals und gehört folglich auch bei einer Variable zur Variable.

x * -y als x * (-y)
x * -y * z als x * (-y) * z
- x * y als -(x*y)
x - - y als x-(-x)
Auch wenn es sich (wie du selbst schreibst) vom Ergebnis gleich bleibt, ist deine dritte Zeile falsch. Diese müsste definitiv als (-x)*y interpretiert werden. Etwas anderes würde es sein, wenn am Zeilenanfang eine 0 stehen würde, dann wäre es ja auch kein unary Minus sondern ein Binary. Dazu gab es vor ein paar Monaten einen ausführlichen Beitrag auf Spiegel.de, kann ihn aber leider nicht mehr finden.
Nino
Beiträge: 1300
Registriert: 13.05.2010 09:26
Wohnort: Berlin

Re: Parser - Unäres und Binäres Minus

Beitrag von Nino »

Josh hat geschrieben:Ein unary Minus hat in jeden Fall höchste Priorität. Wenn du ein Literal hast, ist das unary Minus ja quasi ein Bestandteil des Literals
Nein, nicht nach den gängigen mathematischen Regeln, denn z.B. ist
-3^2 = -(3^2) = -9
[nicht (-3)*(-3) = 9].
Benutzeravatar
STARGÅTE
Kommando SG1
Beiträge: 6996
Registriert: 01.11.2005 13:34
Wohnort: Glienicke
Kontaktdaten:

Re: Parser - Unäres und Binäres Minus

Beitrag von STARGÅTE »

@NicTheQuick: danke, schaue mir den Link in dem Link mal an, der sieht interessant aus.

@Josh: Das mathematische unitäre Minus hat aber die gleiche Priorität wie das binäre Minus oder Plus.
Wenn der Parser -x^y als (-x)^y interpretiert, wäre das fatal (und mathematisch falsch).
Aber ich glaube ich habe in dem Moment wo ich diesen Post mache und den Link von NicTheQuick noch mal anschaue, das Problem gelöst.
Ich kann ja die Priorität wie folgt festlegen:

Code: Alles auswählen

Hoch    ^
         - (unitär)
         *
Tief    + -
S -> E
E -> E '+' T
E -> T
T -> T '*' P
T -> P
P -> '-' P
P -> O ^ P
O -> '(' E ')'
O -> var
Edit: Potenz geändert

So wird zwar aus -x*y -> (-x)*y ist mathematisch aber vertretbar, und -x^y wird als -(x^y) interpretiert.
Weiter geht dann auch x*-y*z -> x*(-y)*z und x^-y^z -> x^(-(y^z)).

Somit hattest du auch recht Josh: "du siehst ein Problem wo keines ist."

Danke an euch beide.
Zuletzt geändert von STARGÅTE am 12.12.2019 18:45, insgesamt 2-mal geändert.
PB 6.01 ― Win 10, 21H2 ― Ryzen 9 3900X, 32 GB ― NVIDIA GeForce RTX 3080 ― Vivaldi 6.0 ― www.unionbytes.de
Aktuelles Projekt: Lizard - Skriptsprache für symbolische Berechnungen und mehr
Benutzeravatar
Josh
Beiträge: 1028
Registriert: 04.08.2009 17:24

Re: Parser - Unäres und Binäres Minus

Beitrag von Josh »

STARGÅTE hat geschrieben:Das mathematische unitäre Minus hat aber die gleiche Priorität wie das binäre Minus oder Plus.
Das gilt vielleicht in der Mathematik, für Programmiersprachen ist es aber falsch. Siehe Operatorenpriorität z.B. von Pb oder C++


@Nino
Dass es im allgemeinen so behandelt wird, ist richtig. Das ist aber eher dadurch bedingt, dass das ^ ein rechtsassoziativer Operator ist und dadurch auch im Shunting-Yard-Algorithmus anders behandelt wird. Für mich ist das eine eher unglückliche Lösung, da -3 für mich nicht eine Zahl mit einem Operator darstellt, sondern einfach eine negative Zahl. Dass es nicht immer so behandelt wird, kannst du hier nachlesen.
Nino
Beiträge: 1300
Registriert: 13.05.2010 09:26
Wohnort: Berlin

Re: Parser - Unäres und Binäres Minus

Beitrag von Nino »

STARGÅTE hat geschrieben:@Josh: Das mathematische unitäre Minus hat aber die gleiche Priorität wie das binäre Minus oder Plus.
Das stimmt nicht. Das unäre Minus kann man wohl am besten verstehen, wenn man es sich als Multiplikation mit -1 vorstellt: -x => -1 * x.
Daraus ergibt sich automatisch die Priorität. Und weil "Punktrechnung vor Strichrechnung" geht, hat das unäre Minus eine höhere Priorität als das binäre Minus.
Josh hat geschrieben:Dass es nicht immer so behandelt wird, kannst du hier nachlesen.
Ich weiß, dass es nicht immer so behandelt wird. Deshalb habe ich absichtlich geschrieben:
nach den gängigen mathematischen Regeln
Damit meine ich die Regeln, wie man sie in der Schule lernt. Diese grundlegenden mathematischen Regeln stehen nicht zur Disposition! Dass es Software gibt die sich nicht an diese Regeln hält, ist ein anderes Problem (das mich erst dann interessieren würde, wenn ich durch widrige Umstände gezwungen wäre solch eine Software zu benutzen).
Antworten