В том, чтобы иметь код, который легко изменять.

Это простое предложение, и, возможно, даже оно не вызовет большое количество споров. Потому что очевидно, что полезно иметь код, который легко изменять. Даже если вы не согласны с тем, что это конечная цель программирования, вы все же, скорее всего, согласитесь с полезностью выражения в целом.

Давайте разберемся. Какую проблему мы пытаемся решить?

Мне кажется, что это фундаментальная проблема программистов. Дело в том, что мы не понимаем, либо же имеем ложные представления о том, зачем мы вообще программируем.

К примеру, когда сварщики варят какую-то конструкцию на стройке, они знают, что эта конструкция необходима для того, чтобы был построен дом. Используют сварку, потому что очень важно, чтобы дом был крепким. Чтобы не было крушения дома. Чтобы люди не погибли при крушении. Это жизненно важно.

Возможно, это покажется слишком очевидным. Возможно, это звучит так, будто я описываю то, что вода мокрая, а небо голубое. Но спросите себя: о чем думают программисты, когда пишут код? Какова конечная цель их деятельности?

«Сделать продукт» — это ответ, который я получал в львином большинстве случаев.

Проблема заключается в том, что само понятие «продукт» постоянно меняется. Вы слышали когда-нибудь такое предложение: «В программировании постоянно только одно: всё всегда изменяется». Точно так же, как ни один бизнес план не выдерживал первого столкновения с потребителем, все проекты всегда изменяются по мере разработки. Появляются новые требования. Баги и ошибки заставляют нас дорабатывать и перерабатывать.

Именно поэтому «сделать продукт» — это крайне неверный способ смотреть на программирование. Этот подход подразумевает, что есть четкий план. Что все расписано и спланировано так, что планы не сорвутся и не изменятся. Что есть требования, которые не поменяются. Что не случится ошибок и багов.

Также это видение не подразумевает того, что понятие «продукт» не только не четкое, не только не изменяется, но и постоянно расширяется. У приложения появляются новые функции и варианты использования, появляются новые сервисы. Бизнес всегда будет пытаться удержать текущих пользователей расширением функционала и улучшением сервиса. Или просто изменяться и адаптироваться под новые рынки.

Я не хочу вас запутать этими рассуждениями. Мысль здесь очень проста: не существует такого понятия как «законченный продукт» в программировании. Наша работа не бывает закончена. Мы можем долго поддерживать текущий продукт, нас могут перебросить на другой или же нас могут попросту уволить. Например, потому что закончились деньги. Но ситуация, когда продукт построен и закончен, случается крайне редко. Наверняка есть исключения из этого правила, но прошу вас обратить внимание, что это именно исключения, подтверждающие правило.

Что я хочу этим сказать и к чему я веду?

Приведу пример из практики. Потому что он поможет применять на практике эти знания и вам.

Недавно я занимался обучением нового сотрудника. Ему была дана задача:

  • в мобильном приложении есть список. В списке отображается лишь один элемент. Остальные элементы списка скрыты.

  • Если нажать «показать весь список», то в списке вместо одного элемента будут отображаться все. Например, 10.

  • Необходимо внести изменение. Нужно, чтобы в самом начале отображался не один элемент списка, а три. То есть заходишь на страницу, видишь три элемента в списке, жмешь кнопку «показать весь список» и показывается уже 10 элементов.

Разработчик подошел к этому вопросу так же, как и, возможно, многие: он написал код так, чтобы список мог принимать аргумент. То есть можно сказать списку, сколько мы хотим элементов в списке, до того как кнопка нажата. Рассуждал он об этом просто: «Я хочу, чтобы у меня с этим списком в будущем больше не было проблем. Если когда‑нибудь надо будет использовать этот список где‑либо еще или использовать несколько списков с разным количеством начальных элементов, то нужно будет просто указать правильный аргумент. Больше никогда не будет проблем с этим элементом». Таким образом он становится future proof.

Это совершенно логично. Это имеет смысл. И это очевидно полезно.

Но когда разработчик спросил меня о том, что я думаю об этом решении, то на удивление оно заставило меня задуматься. В программировании есть много различных принципов. Есть один, который применяется очень редко и зачастую даже вызывает споры: KISS (Keep It Simple Stupid).

То есть для того чтобы взять для отображения лишь один элемент, у нас была вот такая строка:

list.sublist(0, 1)

Чтобы отображать любое количество элементов, мы собрались сделать вот такую строку:

list.sublist(0, amountOfInitialItemsToDisplay)

Казалось бы, изменение не критическое. Но при ближайшем рассмотрении оказалось, что сложность нашего кода резко возрастает. Если ранее у нас был лишь один тест, который имел очень простое описание «если кнопку не нажимали, удостоверься, что отображается лишь один элемент», то теперь нам нужно несколько тестов:

  • «если кнопку не нажимали и если сказано отобразить лишь один начальный элемент то удостоверься, что отображается лишь один элемент»

  • «если кнопку не нажимали и если сказано отобразить 3 элемента, то удостоверься, что отображается три элемента»

  • «если кнопку не нажимали и НЕ сказано что-либо отображать (аргумент отсутствует) то отобрази дефолтное значение — три элемента»

  • «если кнопку не нажимали и если сказано отобразить 0 элементов, то удостоверься что отображается 0 элементов»

  • «если кнопку не нажимали и если было дано негативное число, то кинь ошибку»

  • «если кнопку не нажимали и если было дано число, которое превышает количество элементов списка, то кинь ошибку»

Возможно, последние несколько тестов вам покажутся излишними, и эти ситуации высосаны из пальца. Действительно, я согласен с вами, это так. Но ключевая мысль заключается в том, что раньше у нас таких потенциальных ситуаций, таких проблем и стольких тестов не было. А теперь из-за небольшого изменения логики наш код стал более сложным, у нас больше кода и тестов, которые нужно поддерживать, и разбираться в этом стало труднее.

С обратной же стороны медали у нас есть размышления о том, что мы действительно можем в будущем список изменить (если мы меняем его сейчас, то кто сказал, что мы не изменим его в будущем?), список может иметь разный вид на разных страницах и действительно, он ощущается как не future proof.

Так что же выбрать?

В тот момент я спросил себя: в чем конечная цель программирования? Конечная цель программирования в том, чтобы иметь код, который легко изменять. Если посмотреть на проблему с этой точки зрения, то ответ становится очевиден.

Нужно поменять это:

list.sublist(0, 1)

На это:

list.sublist(0, 3)

Затем обновить один тест, и работа закончена.

Это способ, при котором добавлено наименьшее количество сложности. Это способ, при котором, если нас попросят изменить как-либо этот список, у нас будет наименьшее количество проблем.

Посудите сами: если бы у нас было динамическое количество элементов, то было бы больше логики, больше проверок, больше тестов и больше кода в целом.

То есть когда понадобится изменить этот список (а этот момент обязательно настанет, потому что это аксиома) эта бОльшая сложность нам бы мешала. Пришлось бы её учитывать, писать новые тесты и проверки. Получается, что сложность ведет к бОльшей сложности, и она даже может множиться в геометрической прогрессии.

В конечном итоге несмотря на то, что эти рассуждения очень логичны, они всё же казались мне чем-то неправильным. Словно незаконным. Неужели я учил все различные принципы и получал опыт, чтобы в итоге просто менять один номерок на другой? А как же SOLID? А как же DRY? А может быть, какой-нибудь паттерн программирования использовать? А может быть, извлечь логику создания списка? А может быть, сделать два класса вместо одного? А может, через наследственность как-нибудь? А может, что-нибудь ещё?

В моем конкретном примере все очень просто, и может казаться, будто эти размышления притянуты за уши. Но если отвлечься от специфики моего примера, то станет ясно, что именно так мы зачастую и размышляем. У нас есть свои знания, опыт, идеи и переживания. И очень скоро, если копнуть глубже, становится понятно, что решения мы принимаем в зависимости от множества факторов. Кто-то пишет код так, чтобы перестать переживать о будущем. Кому-то нравится использовать проверенные техники. Кому-то хочется как угодно побыстрее закрыть задачу. Кто-то просто не знает, что делает.

И ни одно из этих решений не делается с позиции здравого смысла. Потому что самое здравое, что мы можем ежедневно делать — это писать код так, чтобы его легко было изменить. Потому что львиную долю своего времени как программисты мы занимаемся тем, что как-то изменяем свой код.

В заключение хочу сказать, что, на мой взгляд, все принципы и лучшие практики, что мы применяем, на самом деле сводятся к мысли, написанной в начале статьи.

DRY == не дублируйте код, пишите так, чтобы изменения не пришлось вносить во множестве мест вместо одного.

Архитектура == правильно делите проект на слои, чтобы изменения в одном слое не затрагивали другие == пишите код так, чтобы его легко можно было менять.

SOLID == пишите код так, чтобы при добавлении функционала мы добавляли классы, а не меняли текущие == пишите классы так, чтобы в проект легко можно было вносить изменения.

Чистый код == пишите код так, чтобы его легко было прочесть и разобраться, что он делает. Чтобы легко можно было внести изменения.

И так далее.

Поэтому каждый раз, когда я задаюсь вопросами о том, как решить какую-либо проблему в коде, я просто спрашиваю себя: «В чем конечная цель программирования?». А затем придумываю способ, при котором код будет легче всего изменить в будущем. Это и вам советую.

Комментарии (52)


  1. freedbrt
    03.10.2023 10:02
    +23

    В чем конечная цель программирования?

    В том, чтобы иметь код, который легко изменять.

    Неверно. Конечная цель программирования это программа которая решает поставленные задачи. Дальше все зависит от разных вводных, поставленные сроки, человеческий ресурс, конечная цель. И от этих условий уже будет зависеть как будет выглядеть код. Но заявлять что конечная цель программирования это код, неверно.


    1. Arkasha
      03.10.2023 10:02
      +4

      С поправкой, что сроки не всегда должны быть, а программист не всегда ресурс. Мы ведь про программирование, а не про бизнес


      1. iig
        03.10.2023 10:02
        +7

        А сварщик, соответственно, не всегда варит необходимые для чего-то конструкции. Иногода он просто для искр, и чтобы шов красивый.


        1. Arkasha
          03.10.2023 10:02
          +1

          А вы еду всегда за зарплату готовите?


        1. amphasis
          03.10.2023 10:02
          +2

          У сварщика в следующем спринте не попросят переварить велосипедную раму в Эйфелеву башню


          1. NIKEtoS1989
            03.10.2023 10:02

            К эйфелевой не попросят, а вот наварить какие-нибудь арматурины, чтоб держалось нормально, а то развалится - вполне могут))


            1. shasoftX
              03.10.2023 10:02
              +2

              Вы сделали клёвый велосипед, он нам нравится. Но приварите к нему люльку и поставьте на него двигатель и тогда вообще будет супер.


    1. undeadlol1 Автор
      03.10.2023 10:02

      Чем "программа" отличается от "продукта" в контексте этой статьи? Мне кажется Вы не читали статью


      1. hlogeon
        03.10.2023 10:02

        Или вы? В статье ведь речь не про продукт, а про код. Нужно ли объяснять, что продукт и код это вообще разные вещи?


    1. titan_pc
      03.10.2023 10:02

      Да. Не всё нормально. Цель программирования же, не разработки)

      Люди пишут код на работе, программируют. Не хотят писать много. А зачем пишут, для чего. Чтоб красивый был. Страшно представить какие библиотеки или фреймворки способны создать такие программисты.

      Про деление на программистов и разработчиков уже все позабыли. Программистов всё больше... им и код изменяемый и супер простой подавай. Гнать их в с++ или ассемблер надо. Пусть познают хоть что есть компьютер. А то как ни спросишь на собесе так про планировщик в ОС мало кто помнит уже, не говоря уже почему двоичка кругом


      1. hlogeon
        03.10.2023 10:02

        А зачем пишут, для чего. Чтоб красивый был. Страшно представить какие библиотеки или фреймворки способны создать такие программисты.

        Какие фреймворки? Наверное красивые))

        А то как ни спросишь на собесе так про планировщик в ОС мало кто помнит уже

        Да и хер бы с ним, если с ОС не работаешь) А - абстракции


  1. myswordishatred
    03.10.2023 10:02
    +6

    В том, чтобы иметь код, который легко изменять.

    А я-то думал в том, чтобы иметь код, который решает задачи. А код, который легко изменять, получить легко. Давайте покажу:

    int main()
      {
        return 0;
      }


    1. Didntread
      03.10.2023 10:02
      +2

      выходит, что даже в таком простейшем случае не так уж легко, так как тут магическое число.


      1. myswordishatred
        03.10.2023 10:02
        +5

        Что ж, верное замечение. Разработал патч, встречайте легкоизменяемый код 2.0:

        int main()
          {
          
          }


        1. Hardcoin
          03.10.2023 10:02
          +3

          Действительно, вы легко его изменили.


  1. YegorP
    03.10.2023 10:02
    +7

    О! Цели vs средства!

    В чём конечная цель молотка или отвёртки? Ни в чём, это инструмент. Не цель, а средство достижения цели. Одно из многих.

    Гибкость кода - размер молотка. И да, минусовой отвёрткой можно закрутить плюсовой шуруп, а кувалдой - забить его аки гвоздь. Уж простите за аналогии. И не забывайте, что аналогия это тоже всего лишь средство, а не цель.

    В контексте цели ценность любого кода околонулевая если он не решает задачу для достижения цели. А цели бывают самые разные. Круглые, квадратные, наземные, подводные...


  1. DrZliden
    03.10.2023 10:02
    +2

    К примеру, когда сварщики варят какую-то конструкцию на стройке, они знают, что эта конструкция необходима для того, чтобы был построен дом. Используют сварку, потому что очень важно, чтобы дом был крепким. Чтобы не было крушения дома. Чтобы люди не погибли при крушении. Это жизненно важно.

    Они знают какой шов использовать и почему(прям чуствую что там есть ГОСТы и прочее, включая какие нибуит наряды и ТЗ). А также технику безопасности которую надо соблюдать. Остальное не думается не его дело, а какого нибудь архитектора, или проектировщика я в стройках не силен. И за это он получит деньги, это он хорошо знает.


    Но спросите себя: о чем думают программисты, когда пишут код? Какова конечная цель их деятельности?

    Закрою задачу вовремя, не огребу люлей, получу зарплату, может даже премию. И буду отдыхать спокойно на выходных, и заниматься своими хобями.


    Мысль здесь очень проста: не существует такого понятия как «законченный продукт» в программировании. Наша работа не бывает закончена

    Очень даже бывает, бывает работа по заказам, заказ выполнен всё до свидания.


    Наверняка есть исключения из этого правила, но прошу вас обратить внимание, что это именно исключения, подтверждающие правило.

    За последние 5 лет было 7 исключений, и всего 3 правила.


    В чем конечная цель программирования?

    Рубить бабло и/или получать удовольствие. Всё остальное, попытки менеджеров вытянуть из работников больше продуктивности, из заказчиков больше денег.


  1. 2medic
    03.10.2023 10:02
    +5

    Интересно, программист, программирующий контроллеры для лифтового оборудования, тоже закладывает идею о том, что он будет постоянно свой код изменять? Или главное получить надёжное и безопасное решение, которое будет способно работать годами без изменений?


    1. iig
      03.10.2023 10:02
      +2

      Хорошо программистам лифтов. У них код получается сразу без багов, и железо никогда не меняется.


      1. 2medic
        03.10.2023 10:02
        +5

        Баги случаются, но ловятся они ещё на стадии отладочного стенда. Ну и железо да, не меняется. Разве что вместе с лифтом или контроллер сгорит. Однако цель программиста в данном случае — это не наплодить абстракций с целью упрощения рефакторинга кода в дальнейшем, а именно получить надёжный код, который решает конкретные задачи. Желательно, чтобы этот код ещё и в контроллер влез. Я вот, помнится, проходя срочную службу в СА запрограммировал сигнализацию на релейной логике, при этом не написав ни строчки кода. Только паяльник и реле. Сильно сомневаюсь, что кому-нибудь захочется изменять программу.


        1. randomsimplenumber
          03.10.2023 10:02

          Сильно сомневаюсь, что кому-нибудь захочется изменять программу.

          Ну да.. поменялись требования? Проще выкинуть и накодить спаять по новому ;)


          1. 2medic
            03.10.2023 10:02
            +1

            :) Особенно если всё собрано с помощью страшного и ужасного

            навесного монтажа


            1. uuger
              03.10.2023 10:02
              +1

              это ещё ничего, хотя бы макетка присутствует, а может быть и вообще 3D конструкция со связями "многие ко многим"

              Hidden text


  1. Fedorkov
    03.10.2023 10:02
    +3

    Цель программирования — это программа, удовлетворяющая потребности пользователя с минимальными затратами.

    Частые изменения в коде — это особенность именно мобильной разработки (и некоторых других областей) — во‑первых, потому что сама область достаточно молодая, и общепринятые практики и фреймворки ещё не до конца устаканились, а во‑вторых, потому что распространение новых версий очень дешёвое.

    Для сравнения, в случе критического косяка ембедщика может потребоваться отозвать партию проданных автомобилей. Поэтому подобные вещи обычно делают в рамках waterfall‑а, а к разработке переходят только после полного описания требований.


    1. Gryphon88
      03.10.2023 10:02
      +1

      Поэтому подобные вещи обычно делают в рамках waterfall‑а, а к разработке переходят только после полного описания требований.

      Не совсем и не всегда. Часто делается прототип на избыточном мк, который в процессе разработки неоднократно перепаивается и вообще причудливо изменяется, а когда заказчик говорит "это оно" — делается итоговая плата, с новым минимальным (ну, почти минимальным, мало ли) мк, с выглаженным и написанным по стандартам кодом. Я был бы рад работать по чистому водопаду, но часто человека. который имеет окончательное правильное понимание о том, как изделие должно работать и как не должно, не существует в природе, всегда получается небольшой НИР/НИОКР.


      1. Fedorkov
        03.10.2023 10:02

        процессе разработки неоднократно перепаивается и вообще причудливо изменяется

        В автопроме электроника обычно делается по ASPICE, там такого практически не бывает.

        Да и в менее критичном к надёжности эмбеддеде изменений в требованиях обычно на порядок меньше, чем в типичной мобильной разработке.


        1. Gryphon88
          03.10.2023 10:02

          в менее критичном к надёжности эмбеддеде изменений в требованиях обычно на порядок меньше, чем в типичной мобильной разработке.

          С этим полностью согласен. Не в последнюю очередь потому, что заказчику при изменении требований нужно оплачивать не только время разработчика, но и комплетующие с платами, иногда еще и стенд, лабораторию и сертификацию. Дополнительные затраты времени и денег режут желание посоветовать поиграть со шрифтами)


          там такого практически не бывает

          Обычно в эмбеддеде требований меньше, точнее они наследуемые: модернизируем устройство или делаем аналог. Если что-то новое и небывалое, то начинается великолепное...


  1. hlogeon
    03.10.2023 10:02
    +7

    В том, чтобы иметь код, который легко изменять.

    Ну вот это утверждение, на котором строится вся статья - явно очень спорное. Кому нужен код, который не работает? Кому нужен код, который легко изменять, но не решает свои задачи? Зачем нужно изменять код, который хорошо решает свою задачу? Из неверного посыла сформирована статья.

    Вообще посыл о том, что программист это человек, который пишет код, а программирование === написание кода - очень вредно и для вас и для читателя. Это приведет вас в карьерный тупик. Программист должен решать задачи бизнеса, используя для этого, в том числе, разработку ПО. Задача программиста - не КОД. Задача программиста - решение бизнес-задачи. Иногда решение заключается в том, чтобы НЕ ПИСАТЬ КОД вообще.


    1. dprotopopov
      03.10.2023 10:02

      Работал и технологом в банках - в основном решал задачи реализации какого либо продукта в виде процесса, проходящего через действия людей и работу средств автоматизации и программ.
      Соответственно на выходе - инструкции для операционистов и бухгалтеров, тз для разработчиков, регламенты для суппорта/админов
      Ну и не с "чистого листа" - надо увязать с имеющимся по возможности


    1. flancer
      03.10.2023 10:02
      +1

      А в чём тогда задача бизнесмена? Найти такого программиста?

      IMHO, автор статьи прав, что в некоторых случаях лёгкость изменения существующего кода становится, по сути, бизнес-задачей разработки ПО. Continuous Deployment/Delivery - это об этом. Кстати, в соседней теме про лунный модуль говорится, что тот внештатно прилунился вследствие программной ошибки и что теперь тамошние разрабы стали опытнее. Так-то может оказаться, что никакой "модели водопада" не существует. Вернее, существует в рамках лишь одной итерации. И это относится и к автопрому, и прочему эмбеддеду. Просто у них итерации идут годами.


      1. hlogeon
        03.10.2023 10:02

        Бизнес не интересует и не должен интересовать КОД вообще ни в каком виде. И про изменяемость вы подменяете понятия. Бизнесу пофигу насколько легко изменять код, его интересует, насколько программа может быстро и легко адаптироваться к новым бизнес-требованиям. Программма может адаптироваться к новым бизнес-требованиям без измнения в коде. Код никого, кроме непосредственно программиста вообще не интересует. Если завтра придумают инструмент, где ты не пишешь код, а рисуешь блок-схемы в Figma и из этого получаешь рабочие программы, все внезапно перейдут на такой инструмент - то и программисты про код забудут.


        1. flancer
          03.10.2023 10:02
          +1

          Бизнесу пофигу насколько легко изменять код, его интересует, насколько программа может быстро и легко

          ОК, что в вашем понимании "код" и что в вашем понимании "программа"? Существует ли программа без кода и кто исполняет такую программу?


          1. hlogeon
            03.10.2023 10:02

            Программа это некий исполняемый файл. Что значит исполняемый файл? То, что он содержит набор инструкций, который может быть выполнен компьютером. Должен ли этот набор инструкций быть понятень человеку? Нет! В моем понимании машинный код не является кодом в том смысле, в котором идет рассуждение в статье. Его уж точно нельзя назвать ни легко изменяемым, ни легко читаемым.


            1. flancer
              03.10.2023 10:02
              +2

              Вот теперь я понял ваш посыл. Программист - это человек, который знает, какую программу нужно запустить, чтобы получить результат, требующийся бизнесу. В таком случае вы правы - такому программисту код ни читать, ни писать, ни изменять нет нужды.


      1. saboteur_kiev
        03.10.2023 10:02

        Continuous Deployment/Delivery - это об этом

        Они не об этом, они о сокращении time-to-market, и это совсем не факт что изменение существующего кода. Это и о новых фичах, когда идет дописывание кода, например.


        1. flancer
          03.10.2023 10:02

          Возможно, это неочевидно, но добавление новых фич - это тоже "изменение существующего кода", как и удаление устаревших фич.

          Я давно в IT и наблюдал эволюцию подхода к кодированию своими глазами. Начиная от "программа должна правильно выполнять свою задачу" (write), через "программа также должна быть ещё и понятна" (read) и до "программа, до кучи, должна быть ещё и легко изменяемой" (modify).

          Потому что главной задачей разработчика ПО является как раз таки поддержание кодовой базы в актуальном состоянии, чтобы она могла продолжать решать задачи бизнеса. Не просто создать приложение "согласно ТЗ" и свалить в закат, а дать инструмент, способный эффективно работать в изменяющейся среде продолжительное время, и поддерживать этот инструмент в актуальном состоянии. Баг и секьюрити фиксы - они ведь тоже про актуализацию состояния ПО в изменяющемся мире.

          Автор поста не побоялся привнести свет в массы и заслуженно получил минусов, потому что массы не любят, когда их просвещают ;) Я-то за его ответ сразу плюс статье поставил, ещё не читая, но я уже больше двадцати лет в IT.


          1. hlogeon
            03.10.2023 10:02

            добавление новых фич - это тоже "изменение существующего кода", как и удаление устаревших фич.

            Все верно, с этим никто не спорит, тезис про  time-to-market это никак не отменяет. Нас одинково интересует  time-to-market как изменения старых фич, так и добавления новых, так и удаления) Это очевидно.

            Я давно в IT и наблюдал эволюцию подхода к кодированию своими глазами. Начиная от "программа должна правильно выполнять свою задачу" (write), через "программа также должна быть ещё и понятна" (read) и до "программа, до кучи, должна быть ещё и легко изменяемой" (modify).

            Хорошо, но как игнорирование тестов в определенной ситуации, или, например, непрохождение code-review улучшает показатели write/read/modify?

            Потому что главной задачей разработчика ПО является как раз таки поддержание кодовой базы в актуальном состоянии, чтобы она могла продолжать решать задачи бизнеса

            Абсолютно верно. Но упущена КРИТИЧЕСКАЯ деталь. Бизнес бывает разный. Это не единая сущность. И у разного бизнеса мало того, что есть разные потребности, бывают еще и разные стадии жизненного цикла. Невероятно странно было бы использовать теже подходы, что используются при разработке банковского ПО для создания лендинга сельского цветочного магазина, не так ли?

             Не просто создать приложение "согласно ТЗ" и свалить в закат, а дать инструмент, способный эффективно работать в изменяющейся среде

            Тут все верно, но опять же нужно уточнить, что понятие "эффективно" для каждой бизнес-задачи будет свое. У всех будут свои метрики. Именно из-за этого уточнения ломается следующая часть утверждения.

            продолжительное время, и поддерживать этот инструмент в актуальном состоянии.

            Далеко не всему бизнесу нужна поддержка ПРОДОЛЖИТЕЛЬНОЕ время. В качестве самого яркого примера я приведу стартап. Вот вы с другом сели и придумали классную идею проекта. Какой бы классной она ни была, с вероятностью примерно в 95% она никому кроме вас с другом нахер не нужна. На этом этапе ваша бизнес-задача не состоит в том, чтобы создать легко поддерживаемый продукт с высоким качеством кода. Почему? Потому что это существенно удорожает разработку именно на ранних стадиях проекта. А у вас нет еще ни одного клиента, прибыли и вы не знаете, сможете ли вообще отбить свои затраты на разработку. Оверинжиниринг на этом этапе - крайне распространенная причина провала проекта вообще. Многие просто даже до рынка не доходят.

            При всем при этом, есть компания, ну, скажем Ericson, которая поставляет в том числе софт для вышек сотовой связи с каких-то бородатых годов, когда еще JavaScript даже в зародыше не было. Очевидно, что в такой корпорации для того софта, подходы к разработке должны быть совершенно иные. И там как раз нельзя делать все то, о чем тут пишет автор. Там надо именно что СТРОГО придерживаться принятых стандартов.

            Автор поста не побоялся привнести свет в массы и заслуженно получил минусов, потому что массы не любят, когда их просвещают ;)

            По причинам, которые я описал выше, я поставил автору минус. Автор посчитал, что суть программирования не в том, что приносить пользу бизнесу исходя из задач, потребностей и жизненного цикла бизнеса, а в какой-то его субъективной красоте кода.

            Для меня это примерно как если бы психолог на сеансе мне сказал, что суть психологии не в том, чтобы помочь клиенту, а в том, что бы за его деньги убедить его в своих(психолога) представлениях о жизни.


            1. flancer
              03.10.2023 10:02

              Вот тут мне сложно вам что-то ответить. Вы почему-то решили, что "легкость изменения кода" подразумевает отказ от тестов и code review. Ни у себя в комментах, ни у автора статьи я не видел такого утверждения. Автор говорил, что писать код нужно так, чтобы тестов нужно было меньше. Вполне здравое утверждение, как по мне.

              Потому что главной задачей разработчика ПО является как раз таки поддержание кодовой базы в актуальном состоянии, чтобы она могла продолжать решать задачи бизнеса

              Прочитайте это ещё раз. Если вы выдающий девелопер, который может написать с одного захода приложение, которое будет работать всегда, то и то вы укладываетесь в это определение. Просто ваши усилия на поддержание после выпуска продукта равны нулю, вы их все вложили до. Никакой КРИТИЧЕСКОЙ детали я не упустил, это вы выдумали её существование. Даже лендинг в сельском магазине со временем нуждается в обновлениях, вот только они уже будут искать другого разраба, потому что имеющийся не берёт телефон. Некоторые могут сказать, что другой разраб сделает другой продукт, вот только решать он будет те же самые бизнес-задачи - лендинг сельского магазина.

              Далеко не всему бизнесу нужна поддержка ПРОДОЛЖИТЕЛЬНОЕ время. В качестве самого яркого примера я приведу стартап. 

              И что? Много вы видели стартапов, которые завелись с одной итерации по методу водопада? В стратапах, как правило, народ плохо представляет, что именно он хочет, и пробует различные варианты, иногда параллельно (A/B-тестирование, например). Там требования к изменяемости кода ничуть не меньше. Кстати, а ПРОДОЛЖИТЕЛЬНОЕ (большими буквами) время - это не меньше скольки? Обычно, продолжительное - это больше нуля. А у вас?

              По причинам, которые я описал выше, я поставил автору минус. Автор посчитал, что суть программирования не в том, что приносить пользу бизнесу исходя из задач, потребностей и жизненного цикла бизнеса, а в какой-то его субъективной красоте кода.

              Ну, вы поняли, как смогли понять, и отреагировали, как смогли отреагировать. Только и всего.


          1. saboteur_kiev
            03.10.2023 10:02

            Continuous Deployment/Delivery это о том, что workflow и архитектура всего продукта сделана таким образом, что каждый или практически каждый коммит в мастер можно деплоить в продакшен (вплоть до автоматического деплоймента в продакшен).
            Без запланированных релизов раз в месяц с шатдаунами, без бюрократических ручных аппрувалов от пачки менеджеров.

            Это не о том, что код легко модифицировать, это о том, что автотестами покрыть надо и код ревью проходить.

            То что при этом коммит может представлять собой кучи реверсинженеринга в легаси, а не легкое изменение - совершенно не очевидно.

            Вот что я хотел сказать про тайм-ту-маркет.


            1. flancer
              03.10.2023 10:02

              TTM - это про то, как каждый коммит (изменение) задеплоить в продакшн максимально быстро. А лёгкость изменения существующего кода - оно разве не про то же? Чем проще тебе менять исходный код, тем быстрее ты выведешь в продакшн новую версию продукта. Просто это один из первых этапов в workflow, но он тоже работает на ту же цель - сокращение TTM. Именно поэтому я и упомянул про Continuous Deployment/Delivery.

              Continuous Deployment/Delivery - это слон, а легкость изменения кода - ну не знаю, бантик на его шее, что ли. Слона видят все, а бантик ещё разглядеть нужно. Если вам "слон" заслонил "бантик", возможно вы просто смотрите на него со стороны хвоста.


  1. Batalmv
    03.10.2023 10:02

    Мне кажется, уже сам вопрос в заголовке уводит автора не туда :)

    Код пишется для решения задачи. Сорян, но такова правда жизни. Именно за это платятся деньги. Но чтобы перейти к тому, как именно ее решить, надо использовать простую вещь.

    Задача == требования. И эти требования делятся на функциональные и нефункциональные. Первые более менее понятно. А вот вторые - и есть собственно "проблематика" :)

    Нефункциональные требования многообразны и тоже влияют на код. Безопасность, отказоустойчивость, нагрузка, совместимость, сопровождаемость, ... Категорий очень много, и нет смысла перечислять. Что весело, часто одни требования противоречат другим. Просто по своей природе, как например безопасность и юзабилити. Чтобы правильно понимать задачу, и соответственно - написать код, который ее решит оптимально, надо просто не полениться и их собрать до того в общем.

    А потом, при возникновении ситцуации "налево пойдешь" / "направо пойдешь" открыть собранные требования, и мысленно, или на бумажке проработать оба варианта. И выбрать тот, который удовлетворяет требования лучше. Если не поможет, наапример, оба варианта равны - спросить заказчика, или подкинуть монетку :)

    Но основное - это понимание, что нефункциональные требования так же важны, а именно они позволяют осознанно выбрать оптимальное решение.


  1. profFortran
    03.10.2023 10:02
    +2

    У самурая нет цели, есть только Путь :-D


  1. kasiopei
    03.10.2023 10:02

    На такой вопрос нельзя дать один ответ, т.к. целей много. Заработать, получить удовольствие.... Это как спрашивать о смысле жизни.


  1. HemulGM
    03.10.2023 10:02

    К примеру, когда сварщики варят какую-то конструкцию на стройке, они знают, что эта конструкция необходима для того, чтобы был построен дом. Используют сварку, потому что очень важно, чтобы дом был крепким. Чтобы не было крушения дома. Чтобы люди не погибли при крушении. Это жизненно важно.

    Сварщики варят чтоб потом было удобно переварить другому сварщику?

    Конечная цель любого программирования - достичь цели, которая решается программированием. Потому что, программирование - это процесс, а результат программирования - программа. Цель любого программирования, как бы это странно для вас не звучало, - программа.

    То, какой код будет написан, насколько удобно его будет нужно менять зависит от многих факторов. Помимо всего этого, если у нас будет совершенный язык и совершенный код, то его вообще не нужно будет менять. Т.е. ваше утверждение априори не верно.


  1. tommyangelo27
    03.10.2023 10:02
    +2

    Идеальный код — это отсутствие кода. В нём нет багов, его не нужно поддерживать, он не превращается в легаси.


    Лично я всегда смотрю — есть ли альтернативы написанию кода — например использовать уже установленную библиотеку, может быть интегрировать сторонний сервис, или даже уговорить клиента купить готовое решение. И только если все эти варианты отпадают — мы садимся писать код.


  1. saboteur_kiev
    03.10.2023 10:02
    +2

    Я не хочу вас запутать этими рассуждениями. Мысль здесь очень проста: не существует такого понятия как «законченный продукт» в программировании. Наша работа не бывает закончена. Мы можем долго поддерживать текущий продукт, нас могут перебросить на другой или же нас могут попросту уволить. Например, потому что закончились деньги. Но ситуация, когда продукт построен и закончен, случается крайне редко. Наверняка есть исключения из этого правила, но прошу вас обратить внимание, что это именно исключения, подтверждающие правило.

    То есть не существует?
    Написал программу, она работает - все, продукт закончен.

    Может быть вы по какой-то причине считаете, что однажды написанная программа должна работать вечно? Но это далеко не всегда так. Если вам нужно чтобы ваша программа работала вечно, это нужно добавлять в тех.задание и соответственно после написания программы ее будут поддерживать. А вот каким способом - их очень много. Можно через время переписать с нуля. Можно изначально разбить программу на микросервисы, что облегчит переписывание. Можно просто патчить под новые версии ОС, или наоборот запускать ее в эмуляторах. Вариантов много

    Или вы хотите сказать что какой-нибудь сварщик, всегда знает зачем нужно сваривать? Так я вас разочарую. Швы портятся. Их периодически нужно переваривать. А то и делать капитальный ремонт. Просто да, мир компьютерных программ слишком молод и слишком быстро меняется. Но программа не обязана быть вечной.

    IMHO ваши очевидные открытия, на самом деле еще одно заблуждение.
    Программисты пишут программы, чтобы решить конкретные задачи. Если за эти задачи платят, то нужно писать так, чтобы заказчик принял написанное. То есть надо выполнять указанное в ТЗ. Опыт позволяет упростить/улучшить контракт на этапе обсуждения ТЗ или условия работы. Но в целом программист или решает задачу или выполняет условия по контракту.
    Ваше представление скорее основано на программистах, которые работают в большой команде, и которым неинтересно разбираться с архитектурой большого проекта - они делают свой маленький кусочек, не особо претендуют на быстрый путь в сеньоры и техлиды. Таких много, может быть даже большинство. Но в любом таком проекте есть тот программист который делает саму задачу, строит архитектуру и делегирует простые задачи вниз, а вы обобщаете поведение джунов и мидлов до самой профессии.

    Написанный однажды стартап, если он взлетел и заработал денег, может оказаться проще переписать с нуля, чем модифицировать. Тем более что на заработанные деньги, можно развернуться, нанять больше разработчиков, и переписать с нуля на основании полученного за это время опыта.

    В моей практике мы делали один из первых интернет магазинов. В начале 2000х. И я помню как писалось ТЗ, как обсуждалось, чтобы прям все учесть. Как с трудом запустилось и наконец принесло прибыль.
    Через год мы заказали новый магазин С НУЛЯ, который написали гораздо быстрее, потому что из ТЗ мы повыкидывали кучу вещей, которые не пригодились. Дописали то, что потребовалось. И новый продукт оказался гораздо более легковесным, отбился в три раза быстрее. Какое-то время его поддерживали, потом все в веб изменилось настолько, что через 3-4 года заказали с нуля еще раз, уже на каком-то общем движке. В данном случае это был правильный путь, более корректный, чем поддерживать легкомодифицирующийся код.

    Таким образом преждевременная оптимизация и продумывание ВСЕГО-ВСЕГО наперед - такое же зло, как и отсутствие опыта при написании понятного и легко поддерживаемого кода. Любой шаг в максимализм - это преступление, а удержать баланс можно только за счет опыта, навыков и проектировании конкретного текущего проекта, а не обобщение опыта, полученного из одной программы на все случаи.


  1. yugo_fx
    03.10.2023 10:02

    5 лет назад, я, будучи зеленым солдатиком джс войск, на фрилансе нашел интересный заказ и написал ужасный, плохо поддерживаемый, трудноизменяемый, но работающий код.

    Он решает задачи заказчика уже 5 лет.

    И вот спустя 5 лет я узнаю, что так и не достиг цели(


  1. Chapaev2023
    03.10.2023 10:02

    в примере со списком надо было переставить sublist(0,1) на sublist(0,3) - как я понял списко меняли в одном месте. если была бы ситуация, когда у вас были два списка с длиной один и три, то тут надо поставить заметку "если будет еще такой список то тут уже пора делать параметризованный список".
    читат я где то то ли методика то ли подход - на такие вещи реагируем только по третьему преценденту


  1. Masonuch
    03.10.2023 10:02

    Цель такова, как и во всем в принципе, сделать так, чтобы с программой было лучше, чем было до программы. Какому-то узкому кругу лиц или более широкому. Вопрос филосовский.


  1. xotkot
    03.10.2023 10:02

    немного вспомнилось о докладе - "Simple Made Easy" - Rich Hickey (2011)


  1. raqeta
    03.10.2023 10:02

    Единственная цель программирования — автоматизация. Больше нет.

    Программирования нет, где можно нанять и посадить человека.

    Например, было так, при приеме ордеров на бирже, записывали ставку в книжку, если цена покупки и продажи совпадали, происходил обмен. Но с автоматизацией быстрее и больше.

    Остальное красивости.


  1. bambruysk
    03.10.2023 10:02

    У программирования нет цели, у программирования есть только путь.