Ostatnio nudziłem się i zrobiłem programik do obliczania wartości wyrażeń matematycznych.
(http://4programmers.net/Delphi/Gotowce/Obliczanie_wartości_wyrażenia).
Nie wiem nawet, czy ktoś spojrzał na to :D, dlatego prosiłbym o ocenę, jak to napisałem, co można by poprawić, etc.
Wszelka krytyka mile widziana, ponieważ aktualnie robię większy projekt oparty o to i wolałbym, aby było poprawione i usprawnione tam, gdzie się tylko da ;)
tak na szybko to
- czemu nie klasa
- czemu nie TStack z contnrs tylko tablica dynamiczna - tak to musiałeś pisać większość kodu od nowa
- większość funkcji masz metodą kopiegopasta - pop-pop2, push-push2
- isNumber jest niepoprawna - przepuści np. 123.45.6 - masz przecież TryStrToFloat, Val i podobne
- GetFunctionNum też nie jest do końca poprawna - jak ktoś wpisze
Sin
zamiastsin
to już nie ma takiej funkcji - użyj SameText
Samej zamiany na ONP nie chce mi się sprawdzać :p
Zlamione NWW.
Użyj: NWW(a, b) = a / NWD(a, b) * b
Nowa wersja.
Kod:
http://pastebin.com/UbM6TaJJ
Instrukcja obsługi:
http://4programmers.net/Delphi/Gotowce/Obliczanie_wartości_wyrażenia
Liczę na kolejne opinie i sugestie ^^
Btw, cd.punktu 4 od Misiekd - zapomniałem poprawić; zrobi się jutro ;)
dokumentacja napisał(a)
Procedure SetRPN(Expr: String); → ustawia wartość RPN na Expr
Function EvalRPN: Extended; → oblicza wyrażenie ONP znajdujące się w zmiennej RPN
Zmienna globalna jako niejawny parametr funkcji?? Wywal to, dobrze Ci radzę.
Function EvalExpr(Expr: String): Extended; → oblicza wyrażenie matematyczne
Brzmi fajnie, nie ma globalnego stanu. Popatrzmy w kod:
Function TExpressionParser.EvalExpr(Expr: String): Extended;
Begin
ExprToRPN(Expr);
Result := EvalRPN;
End;
End.
Co się dzieje? Niejawnie zmieniana jest globalna zmienna RPN, po czym wywoływana jest funkcja niejawnie korzystająca z niej jako parametr. Pięknie.
Co powiesz na taki kod:
SetRPN("2 + 2");
a := EvalExpr("3 * 8");
b := EvalRPN(); (* Zonk *)
dalej:
f_SQRT = 0;
f_SIN = 1;
f_COS = 2;
f_TAN = 3;
f_ASIN = 4;
f_ACOS = 5;
f_ATAN = 6;
f_MIN = 7;
f_MAX = 8;
f_NWW = 9;
f_NWD = 10;
f_SQR = 11;
f_ROUND = 12;
f_PI = 13;
f_ABS = 14;
Functions : Array[0..014] of String = ('sqrt', 'sin', 'cos', 'tan', 'asin', 'acos', 'atan', 'min', 'max', 'nww', 'nwd', 'sqr', 'round', 'pi', 'abs');
FunctionsParam: Array[0..High(Functions)] of Integer = (1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 1, 1, 0, 1);
Zastanów się nad zrobieniem klasy TOperation z polami ID : String oraz wirtualną metodą Execute(param : Array of Number) : Number
Co chwilę w kodzie pojawia się idiom
ErrorCode := ERROR_WRONG_OPERATORS;
ErrorInfo := Pos;
Może jakaś funkcja SetError(code, info)?
Tyle uwag na razie, wybacz wszystkie pseudopascalowe wstawki jakie napisałem, ostatni raz w tym języku pisałem baardzo dawno.
ciekawe :)
Wersja 0.4
Kod: http://pastebin.com/Szc5YWMz
Instrukcja obsługi: http://4programmers.net/Delphi/Gotowce/Obliczanie_wartości_wyrażenia
Możliwe, że coś pominąłem, ale się spieszyłem