открытое письмо, блин :)
@jitbit написал как он решал боль с тринарным оператором:
https://t.me/devfounder/18
У меня есть пара комментариев, которые явно не тянули на отдельную статью, но теперь можно :)
Тут, безусловно, опыт накладывает отпечаток, но отсутствие правой части плохо тем, что возникает место, где что-то подразумевается.
Это плохо по многим причинам, но основная причина в том, что разные люди могут подразумевать разное, а компилятор совсем другое :)
Я стараюсь придерживаться принципа more verbose и искренне вам советую.
Например, в нашем конфиге линтера включено правило, которое запрещает в тринарных операторах писать так:
a ? 1 : 2
нужно обязательно написать конкретно:
a != null ? 1 : 2
Больше букв? Больше. Но, как говорится, есть нюанс :)
"" ? 1 : 2
Результат равен 2.
оО скажете вы. «Сюрприз!», - скажет js.
Или еще одна вещь, которая пила мне кровь, и мы, кажется, тоже запретили ее в линтере.
Это дефолтные значения параметров в функциях.
В питоне, например, все библиотеки забиты функциями с дефолтными параметрами и это одна из хороших причин не любить этот язык.
Что тут такого?
Описана, например, функция getData(query, limit=100), которая, допустим, выбирает что-то из базы с заданным лимитом. В коде она будет выглядеть как
getData(‘...’)
Сколько времени придется потратить, прежде чем новый программист в этом проекте поймет почему у него иногда возвращаются не все данные?
Зависит от опыта, но это явно не 5 минут.
Как сэкономить себе и другим нервы и время? заведите рядом константу или передавайте это значение из конфига.
Еще одно правило, экономящее нервы, запрещало писать функции без лямбды в качестве параметров функций. Например:
1,2.map(console.log)
Что ожидается? Две строки со значениями элементов в консоли. А что будет?
1,0
2,1
wtf? В колбек map передается две переменных - значение и номер в массиве. А console.log выведет все, что ей передали.
Конкретно в этом случае это безвредно, но так будет не всегда :)
И последний пример, показывающий важность статического анализа.
Есть в js вещь, которую без типов и стат анализа не сделать, и она портит жизнь всем js/flow/ts разработчикам в мире. Это конструкция вида
array.includes(value)
Не знаю по какой причине во flow этого нет (хз как в ts, но думаю, что тоже), но сигнатура функции позволяет проверять на вхождение в массив элементов типов, отличных от типа массива. В итоге получается, что ты пишешь
1,2.includes(object)
и у компилятора это не вызывает вопросов, хотя ты явно хотел не этого, а чего-то вида
1,2.includes(object.field)
Один раз я потратил 5 часов, когда искал эту багу.
После чего я попросил запилить ворнинг для линтера, который будет орать на все .includes
Лучше я проверю это место руками и задизейблю это правило для конкретной строки, чем пропущу это место.
Какие выводы, кроме того, что js и питон плохие языки и даже статические типизаторы вас не спасут?
1) изучайте разные языки для расширения кругозора. В функциональных языках невозможно делать if без else и рекурсивную функцию без описанного условия выхода. И тринарному оператору нельзя существовать без правой части.
Если вы будете делать так же в своем коде, завтрашний вы скажет вам спасибо :)
2) не экономьте на символах. Чем более точно вы опишете компилятору, что вы от него хотите, тем спокойнее будет ваш сон :) Даже если компилятор поймет укороченную версию, завтрашний вы можете об этом забыть. Не говоря уже о новых сотрудниках на проекте.
3) используйте статические анализаторы и статическую типизацию в языках, где нет нормальной типизации. Велика вероятность, что это сэкономит вашей компании много денег, а вас не лишит места в этой компании :)
Кстати, скоро я выкачу первую версию статического анализатора для sql, поэтому готовьте ваши запросы :)
Post #261
369