-
Notifications
You must be signed in to change notification settings - Fork 28
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Siarhiej Kresik #32
base: master
Are you sure you want to change the base?
Siarhiej Kresik #32
Conversation
@@ -0,0 +1,34 @@ | |||
.DEFAULT_GOAL := run |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
С моей точки зрения в данном случае можно было обойтись без makefile.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Мне так было зручней ставіць/выдаляць праграму, правяраць, як яна працуе, запускаць pycodestyle.
} | ||
} | ||
|
||
MODULE = { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Я не вижу большого смысла в вынесении параметров для ArgumentParser
в отдельные глобальные словари. Их можно было разместить прямо в аргументах функции.
def is_numeric(obj) -> bool: | ||
"""Return `True` if a object is one of numeric types.""" | ||
|
||
return isinstance(obj, (NUMERIC_TYPES)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Для чего NUMERIC_TYPES
обернут в скобочки?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Яны там лішнія. Засталіся, відаць, пасля таго, як вынес tuple ў канстанту.
from .punctuation import Comma | ||
|
||
|
||
__all__ = [ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
__all__
содержит все значения, которые есть в этом модуле. То есть в целом нет смысла определения этой переменной
self.const_registry = const_registry | ||
|
||
def nud(self, parser, token): | ||
"""""" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Пустой докстринг
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Я так і не прыдумаў, як гэтыя штукі абазваць :D
|
||
try: | ||
self.calculator = calculator(modules) | ||
return |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
В данном случае return
можно опустить
except Exception as exc: | ||
err_msg = str(exc) | ||
|
||
self.on_error(err_msg) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Очень странный подход, который сильно запутывает.
В данном случае получается, что последняя строчка функции исполняется только в случае если было отловлено исключение, а при нормальном исполнении функции до этой строчки исполнение не дойдет.
Это мелочь, но лично для меня это смотрится странно
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Але па-другому б у канцы кожнага except
прыйшлося б пісаць self.on_error(err_msg)
.
|
||
self.on_error(err_msg) | ||
|
||
def on_success(self, result): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Я думаю, что такие однострочные методы только усложняют код.
В данном случае этот метод вызывается только в одном месте и все, что он делает, это проксирует вызов другому методу. То есть фактически он ничего не делает.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
З аднаго боку, яно, вядома ж, і так. Але скажам, заўтра вам скажуць, што калькулятр мае пісаць логі і пасылаць рэзультат/памылку на сервер. І калі для памылкі ёсць куды засунуць логіку, то для рэзультата трэба будзе разбірацца ў кодзе і думаць, куды яе напісаць.
|
||
sys.exit() | ||
|
||
def prefix_err_msg(self, msg): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Аналогичная ситуация. Метод вызывается только в одном месте и делает только конкатенацию двух строк.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Функцыя прэфіксатар робіць роўна тое, што і трэба — дадае прэфік ERROR:
.
Лёгка тэставаць, лёгка мяняць, адразу відаць, што робіць, не мяшаецца з другім кодам.
Другая рэч, што можа ёй ня месца ў класе, але гэта заўсёды праблема — куды засунуць падобную функцыю, калі яна адна-дзве такія.
UNDERSCORE = '_' | ||
|
||
|
||
def iter_uniq(iterables): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Эту же функциональность делает set
-- хранит уникальные значения.
import re | ||
|
||
|
||
def list_sorted_by_length(iterable) -> list: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Функция вызывается только в одном месте и делает ровно одно действите -- сортировку с помощью стандартной функции. Можно было обойтись прямым вызовом sorted
return sorted(iterable, key=len, reverse=True) | ||
|
||
|
||
def construct_literals_list(literals): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Такая же ситуация
|
||
@unittest.skip('not implemented') | ||
def test_peek(self): | ||
pass |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
not implemented
raise CalculatorCalculationError(err_msg) | ||
|
||
|
||
def calculator(modules_names=None): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Нэйминг немного запутывает. В данном модуле есть класс калькулятор
и функция калькулятор
В основном код достаточно чистый и легко читаемый со стилистической точки зрения, однако я вижу тут одну комплексную проблему. Код ощущается перенагруженным, большая его часть можно сказать ничего не делает. |
Description
A command-line calculator implemented using Top Down Operator Precedence parsing algorithm (Pratt parser).
Minimal requirements
expression string as an argument and prints evaluated result:
$ pycalc '2+2*2' 6
error explanation with "ERROR: " prefix and exit with non-zero exit code:
Mathematical operations calculator must support
+
,-
,*
,/
,//
,%
,^
) (^
is a power).<
,<=
,==
,!=
,>=
,>
).abs
andround
.math
(trigonometry, logarithms, etc.).Non-functional requirements
argparse
module.Distribution
setuptools
.pycalc
.Codestyle
pycodestyle
utility for self-check).Optional requirements
These requirement is not mandatory for implementation, but you can get more points for it.
Support of functions and constants from the modules provided with
-m
or--use-modules
command-line option.This option should accept names of the modules which are accessible via
python standard module search paths.
Functions and constants from user defined modules have higher priority in case of name conflict then stuff from
math
module or built-in functions.(bug: -m <module_name> won’t override built-in or standard <module_name>)
In this case
pycalc
utility should provide the following interface:Examples: