В большинстве случаев «магические числа» конечно же нужно выделять в отдельные константы, но этот пример:
StringBuilder builder= new StringBuilder();
for (int i = days; i > 0; i /= 10) {
builder.insert(0, i % 10);
}
на мой взгляд, как раз наоборот является примером, где лучше использовать 10 вместо константы (банально сложно придумать адекватное название для 10 в данном контексте), а так в принципе понятно, что этот цикл откусывает от числа последнюю цифру на каждой итерации и вставляет ее в начало строки (в конченом итоге это просто:
На моменте с FunQL закатил глаза: "О боже, и тут без собственного языка не обошлись". То, что это собственный язык, к сожалению, тоже не сразу очевидно (ссылка с документацией на домен ozma.io намекает, но, кажется, лучше это явно проговорить). Как я понял собственный язык нужен в основном из-за атрибутов (кстати, пояснение, как аттрибут выглядит синтаксически, следует заметно позже нескольких примеров запросов).
Для такой тяжеловестной абстракции, как собственный язык, хочется сразу увидеть рационализацию необходимости такого решения. А точно ли нельзя было сделать на чем-то существующем? Нельзя ли было сделать какую-то мета-таблицу, где в специальной колонке указывался бы тип запроса? (который @type=’board’, @type=’form’)
Или чтобы это вообще был не SQL, а ЯП общего назначения? SQL это же про данные, а не логику. А то получается, что мы GUI пытаемся на SQL нарисовать. Короче, да, почему тут SQL я не очень понял. (не отрицаю что мое непонимание возможно исходит от слабого познания SQL. С SQL мне мало приходилось работать)
Я бы еще отметил, что наследование классов — впринципе очень опасная операция, с которой надо обращаться аккуратно. Когда вы наследуюте один класс от другого, то вы подразумеваете, что наследуете то, как там ваш родитель "работает под капотом". Иначе говоря вы наследуете не только семантику, но еще и реализацию этой семантики.
Выражать конструкции вида "квадрат это прямоугольник" путем наследования классаSquare от классаRectangle — опасно (это как раз то, что приводит к тому, что класс Square в реализации в статье работает не оптимально и требует в два раза больше памяти чем нужно).
Правильнее определить два интерфейса (я думаю не стоит упоминать, что интерфейсы еще и позволяют Square унаследовать дополнительно от Rhombus...):
interface Rectangle {
int getHeight();
int getWidth();
int perimeter();
}
interface Square extends Rectangle {
int getSideLength();
default int getHeight() { return getSideLength(); }
default int getWidth() { return getSideLength(); }
}
И после этого писать реализации RectangleIml и SquareImpl под каждый. Причем на практике допустимо реализовать SquareImpl путем наследования от RectangleIml, это обычный инженерный trade-off между "написать поменьше кода" и "покушать меньше памяти". Просто академически это неправильно.
Ну а про мутабельность Rectangle и Squareсверху умные люди уже написали. В данном случае иммьютабельность — это не просто поклон моде, а вынужденная необходимость, чтобы Rectangle и Square оставались прямоугольником и квадратом в математическом определении соответственно. Если есть желание по существующему объекту интерфейса Rectangle получить другой Rectangle, с измененной высотой, то это можно делать имьютабельно путем добавления метода в интерфейс Rectangle:
/**
* Creates new Rectangle which inherits width from {@code this} Rectangle but has {@code newWidth}
*/
Rectangle rectWithWidth(int newWidth);
За арч и двор стреляю в… А вообще кто это вам наговорил таких гадостей про арч? Очень надежная система. Стоит больше двух лет с более 1500 установленых пакетов, никак нареканий и проблем.
Если вы про обычную тетрадь, то да — можно использовать версию 2.1 для правшей, а версию 2.2 для левшей. И все будет работать даже в обычной тетради, только лист придется поддерживать в вертикальном положении.
Блочная тетрадь — потенциально бесконечный поток листов, у него нет конца. Вы не знаете в какой момент надо "развернуться" и писать в другом направлении (вы можете попытаться это угадать и, но если вы не угадаете, то у вас будет либо растрата ресурсов, либо вам не хватит листов). А если вы про обучную тетрадь, то в ней даже факт того, что вы пишете только на одной стороне листа не спасает (листья то закреплены)
Разве страницы «обычно» перелистываются не влево (справа налево=влево)?
Влево, вправо… Вот скажите свайп вправо это когда палец провели слева направо или наоборот? Я вот не знаю и каждый раз уточняю у говорящего, потому что каждый называет это по своему. Именно для этого я и ввел секцию с терминологией, чтобы исключить недопонимания.
Нелокальность больше, чем при обычном способе записи
Да, соглашусь, замечание по делу. Небольшой эффект нелокальности есть. Но можно заметить, что если мы хотим удовлетворять основному требованию, то нам непременно придется "скакать" по страницам, т.е. нельзя придумать такой способ, который бы удовлетворял и локальности, и основному требованию.
это плохо, потенциально можно словить nullptr dereference
Неа, nullptr dereference вы не словите, даже если если там null. sizeof() даже не пытается вычислять значение аргумента, а просто по честному подставляет его размер на эта преобразования в ассемблер. Именно по этому я пишу обращения в функции malloc и ей подобным в духе:
на мой взгляд, как раз наоборот является примером, где лучше использовать 10 вместо константы (банально сложно придумать адекватное название для 10 в данном контексте), а так в принципе понятно, что этот цикл откусывает от числа последнюю цифру на каждой итерации и вставляет ее в начало строки (в конченом итоге это просто: ).
На моменте с FunQL закатил глаза: "О боже, и тут без собственного языка не обошлись". То, что это собственный язык, к сожалению, тоже не сразу очевидно (ссылка с документацией на домен ozma.io намекает, но, кажется, лучше это явно проговорить). Как я понял собственный язык нужен в основном из-за атрибутов (кстати, пояснение, как аттрибут выглядит синтаксически, следует заметно позже нескольких примеров запросов).
Для такой тяжеловестной абстракции, как собственный язык, хочется сразу увидеть рационализацию необходимости такого решения. А точно ли нельзя было сделать на чем-то существующем? Нельзя ли было сделать какую-то мета-таблицу, где в специальной колонке указывался бы тип запроса? (который
@type=’board’
,@type=’form’
)Или чтобы это вообще был не SQL, а ЯП общего назначения? SQL это же про данные, а не логику. А то получается, что мы GUI пытаемся на SQL нарисовать. Короче, да, почему тут SQL я не очень понял. (не отрицаю что мое непонимание возможно исходит от слабого познания SQL. С SQL мне мало приходилось работать)
Был бы рад ссылкам
Я бы еще отметил, что наследование классов — впринципе очень опасная операция, с которой надо обращаться аккуратно. Когда вы наследуюте один класс от другого, то вы подразумеваете, что наследуете то, как там ваш родитель "работает под капотом". Иначе говоря вы наследуете не только семантику, но еще и реализацию этой семантики.
Выражать конструкции вида "квадрат это прямоугольник" путем наследования класса
Square
от классаRectangle
— опасно (это как раз то, что приводит к тому, что классSquare
в реализации в статье работает не оптимально и требует в два раза больше памяти чем нужно).Правильнее определить два интерфейса (я думаю не стоит упоминать, что интерфейсы еще и позволяют
Square
унаследовать дополнительно отRhombus
...):И после этого писать реализации
RectangleIml
иSquareImpl
под каждый. Причем на практике допустимо реализоватьSquareImpl
путем наследования отRectangleIml
, это обычный инженерный trade-off между "написать поменьше кода" и "покушать меньше памяти". Просто академически это неправильно.Ну а про мутабельность
Rectangle
иSquare
сверху умные люди уже написали. В данном случае иммьютабельность — это не просто поклон моде, а вынужденная необходимость, чтобыRectangle
иSquare
оставались прямоугольником и квадратом в математическом определении соответственно. Если есть желание по существующему объекту интерфейсаRectangle
получить другойRectangle
, с измененной высотой, то это можно делать имьютабельно путем добавления метода в интерфейсRectangle
:За арч и двор стреляю в… А вообще кто это вам наговорил таких гадостей про арч? Очень надежная система. Стоит больше двух лет с более 1500 установленых пакетов, никак нареканий и проблем.
Если вы про обычную тетрадь, то да — можно использовать версию 2.1 для правшей, а версию 2.2 для левшей. И все будет работать даже в обычной тетради, только лист придется поддерживать в вертикальном положении.
Блочная тетрадь — потенциально бесконечный поток листов, у него нет конца. Вы не знаете в какой момент надо "развернуться" и писать в другом направлении (вы можете попытаться это угадать и, но если вы не угадаете, то у вас будет либо растрата ресурсов, либо вам не хватит листов). А если вы про обучную тетрадь, то в ней даже факт того, что вы пишете только на одной стороне листа не спасает (листья то закреплены)
Влево, вправо… Вот скажите свайп вправо это когда палец провели слева направо или наоборот? Я вот не знаю и каждый раз уточняю у говорящего, потому что каждый называет это по своему. Именно для этого я и ввел секцию с терминологией, чтобы исключить недопонимания.
Проблему мотания листка из стороны в сторону, когда идет переход между разворотами
Да, соглашусь, замечание по делу. Небольшой эффект нелокальности есть. Но можно заметить, что если мы хотим удовлетворять основному требованию, то нам непременно придется "скакать" по страницам, т.е. нельзя придумать такой способ, который бы удовлетворял и локальности, и основному требованию.
Неа, nullptr dereference вы не словите, даже если если там null. sizeof() даже не пытается вычислять значение аргумента, а просто по честному подставляет его размер на эта преобразования в ассемблер. Именно по этому я пишу обращения в функции malloc и ей подобным в духе: