Unäre Negation erkennen
-
Hallo,
ich möchte einen mathematischen Ausdruck (als String) parsen. Dabei will ich zwischen einer Subtraktion und einer unären Negation unterscheiden. Das ist etwas problematisch, da ja beide als Zeichen '-' haben.Bsp:
Subtraktion: 3-4 (dürfte klar sein..)
unäre Negation: -4, -(...), -funktion(...), 3*-4 uswGehe ich richtig in der Annahme, dass es eine unäre Negation sein MUSS, wenn vor dem '-' steht: nichts, +, -, *, /, ^, (, Funktion
Ich würde die oben gegebenen Bedingungen für jedes '-' überprüfen und so entscheiden, von welcher Art es ist. Ist das die beste Lösung?
MfG,
Max// Edit: Denkfehler behoben^^
-
es ist dann unär, wenn vor dem zeichen kein gültiger ausdruck abgeschlossen wird.
-
unitarier schrieb:
es ist dann unär, wenn vor dem zeichen kein gültiger ausdruck abgeschlossen wird.
bei "3-4" ist 3 aber ein gueltiger Ausdruck
Wenn du die Grammatik fuer deine Ausdruecke geschickt waehlst, loest sich das Problem eigentlich sowieso in Luft auf
Wie schaut denn deine Grammatik zur Zeit aus?
-
Blue-Tiger schrieb:
unitarier schrieb:
es ist dann unär, wenn vor dem zeichen kein gültiger ausdruck abgeschlossen wird.
bei "3-4" ist 3 aber ein gueltiger Ausdruck
deswegen ist dieses minus ja auch nicht unär.
-
ripmav schrieb:
Gehe ich richtig in der Annahme, dass es eine unäre Negation sein MUSS, wenn vor dem '-' steht: nichts, +, -, *, /, ^, (, Funktion
Das mit der Funktion ist nicht richtig. Sonst wäre ja zB sin(x)-3 kein vernünftiger Ausdruck (und das sollte ja schon ein vernünftiger Ausdruck sein und bei genauerem Betrachten sieht man auch, dass das - hier binär sein sollte :)).
Aber wie Blue-Tiger schon gesagt hat: Schreib dir die Grammatik mal auf.
-
Danke für die Antworten!
Ich meine allerdings mit Funktion vor dem '-' NUR eine Funktion (keine Klammern)
Bsp: sin-3
Weil bei sin(x)-3 wäre das Zeichen vor dem '-' ein ')' -> Es wäre eine Subtraktion bei mir.Ich unterscheide folgende Zeichen(-ketten):
{"(", 1, I_OPEN_BRACKET }, {")", 1, I_CLOSE_BRACKET }, {"+", 1, I_ADDITION }, {"-", 1, I_SUBTRACTION }, // <- Daraus wird nach dem Check möglicherweise I_NEGATION {"*", 1, I_MULTIPLICATION }, {"/", 1, I_DIVISION }, {"%", 1, I_MODULO }, {"^", 1, I_POWER }, {"sin", 3, I_SIN }, {"cos", 3, I_COS }, {"tan", 3, I_TAN }, {"asin", 4, I_ASIN }, {"acos", 4, I_ACOS }, {"atan", 4, I_ATAN }, {"abs", 3, I_ABS }, {"ln", 2, I_LN }, {"log", 3, I_LOG }, {"sgn", 3, I_SGN }, {"sqrt", 4, I_SQRT } // Außerdem wird auch auf I_VARIABLE und I_NUMBER geprüft.
// Edit:
Hier ist die Funktion, die überprüft, ob eine unäre Negation vorliegt:void CheckUnary(SInstruction& instr, const SInstruction& before) { if (instr.type != I_SUBTRACTION) return; if (before.type == T_NOTHING || before.type == I_OPEN_BRACKET || IsOperator(before) || IsFunction(before)) { instr.type = I_NEGATION; } }
Genauso könnte man auf ein unäres '+' überprüfen.
-
volkard schrieb:
Blue-Tiger schrieb:
unitarier schrieb:
es ist dann unär, wenn vor dem zeichen kein gültiger ausdruck abgeschlossen wird.
bei "3-4" ist 3 aber ein gueltiger Ausdruck
deswegen ist dieses minus ja auch nicht unär.
hoppla, hatte mich verlesen
-
Hier ist die Funktion, die überprüft, ob eine unäre Negation vorliegt:
Wenn du vorher in einen syntax tree parsen würdest, bräuchtest
du nur die Anzahl der Argumente zählen: wenn == 1, dann unär.
-
Wenn du vorher in einen syntax tree parsen würdest, bräuchtest
du nur die Anzahl der Argumente zählen: wenn == 1, dann unär.Das ist mir nicht möglich, da ich die Funktion mit dem Shunting Yard Algorithmus parse. Dabei muss bekannt sein, wieviele Parameter eine Funktion (bzw. ein Operator) hat. Bei - ist das aber nicht klar: Es könnte eine Subtraktion sein (2 Parameter) oder eine unäre Negation (1 Parameter)..
Auf jeden Fall funktioniert mit der Hilfsfunktion, die '-' richtig zuweist alles.
Ich bin die Logik mehrmals durchgegangen und habe viele möglichen Terme durchprobiert. Es dürfte alles stimmen
-
ripmav schrieb:
Wenn du vorher in einen syntax tree parsen würdest, bräuchtest
du nur die Anzahl der Argumente zählen: wenn == 1, dann unär.Das ist mir nicht möglich, da ich die Funktion mit dem Shunting Yard Algorithmus parse. Dabei muss bekannt sein, wieviele Parameter eine Funktion (bzw. ein Operator) hat.
Ich kenne diesen Algorithmus jetzt zwar nicht, aber warum weisst du nicht wieviele Parameter der unaere operator - hat?
Der unaere op - und der binaere op - koennen ja nie an der selben stelle stehen...
Wenn ich mir den wikipedia Artikel so durchlese - ganz so primitiv wie "wenn operator, dann pushe auf stack" geht es natuerlich nicht. Aber du weisst ja ob da ein binaerer oder ein unaerer operator kommt. Du schaust dir einfach an was du als letztes gepusht hast. Wenn es nichts oder ein operator oder ein ( war, dann ist es ein unaeres - wenn es etwas anderes war, ist es ein binaerer. uU muss man ein paar spezialfaelle beruecksichtigen - aber generell erkennst du aus dem kontext um was es sich fuer einen operator handelt.
-
Genau das mache ich auch. Ich bin so frei und zitiere mich selbst:
Gehe ich richtig in der Annahme, dass es eine unäre Negation sein MUSS, wenn vor dem '-' steht: nichts, +, -, *, /, ^, (, Funktion