четверг, 19 августа 2010 г.

[prog.thoughts] О предсказании сроков написания программ

В программировании есть несколько очень сложных проблем, не имеющих однозначного решения. Как то: определение настоящих желаний заказчика; выбор хороших имен для идентификаторов; предсказание сроков реализации; объяснение подчиненному того, что ты от него хочешь получить (см.первый пункт списка)… Сегодня выдаю поток сознания на тему того, почему лично я никогда не угадываю со сроками написания программ.

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

Это вопрос веры еще и потому, что невозможно представить себе точный объем предстоящей работы. Во-первых, есть семантический разрыв. На эту тему я уже писал почти год назад. Но влияние этого разрыва на точность сроков чрезвычайно велико – объем фактической работы отличается от объема предполагаемой работы в разы.

Во-вторых, далеко не всегда есть вообще четкие идеи о том, что и как будет делаться. Вот, например, я недавно обнаружил, что правила маршрутизации сообщений в нашем шлюзе достигли предела нормального восприятия. Стало понятно, что их нужно упрощать и приводить к какому-то другому виду. Но к какому? Идей нет, их еще предстоит выносить и родить. Сколько на это потребуется времени? Без понятия. Может быть день, может быть неделя, может быть месяц. Я могу исходить только из собственной самоуверенности – когда-то мне потребовалось около месяца на рождения некоего алгоритма. По сложности задачи кажутся мне равнозначными. Поэтому я верю в то, что месяц на проектирование новой формы правил маршрутизации – это реально. Но это только вера, она не подкреплена никакими выкладками.

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

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

  • рабочих дней в неделе всего пять. Т.е. месяц – это не 30 дней, а около 20 рабочих. Почему-то я упорно не могу заставить себя разделять выходные и рабочие дни, наверное, большой опыт авральных проектов сказывается :(
  • на определенных стадиях проектов эффективное рабочее время будет составлять всего 2-3, в лучшем случае 4 часа в день. Т.е., если для проектирования решения потребуется 16 часов, то это не два рабочих дня, а 5-8 рабочих дней;
  • расходы времени на коммуникации с коллегами. Между тем, расходы собственного рабочего времени при этом растут просто катастрофически. Например, если ко мне обращается подчиненный с вопросом на 20 минут обсуждения, то чтобы вернуться к работе мне требуется, как минимум, раза в два больше времени. Следует добавить сюда и огромный расход энергии на то, чтобы быстро включиться в тему нового разговора;
  • непредвиденные технические проблемы. Начиная тем, что ты сам неверно прочитал документацию и написал код в ошибочных предположениях, заканчивая глюками или недокументированными особенностями сторонних библиотек. Из этой же оперы и ошибки в технических предположениях: например, почему-то предполагалось, что асинхронный I/O в конкретных условиях будет выгодным, а на деле вышло наоборот;
  • разнообразные личные обстоятельства и житейские форс-мажоры – сам заболел или с ребенком нужно посидеть, или за какими-нибудь справками нужно бегать в рабочее время;
  • элементарное отсутствие желания работать. Да, если задача захватила тебя полностью и ты желаешь ее натянуть по самые гланды – тогда душа поет и руки сами код пишут. А если нет? Чем старше становишься, чем больше сделанного за плечами, тем меньше адреналина от новых задач. Посему из 8-ми часов рабочего времени (минус все вышесказанное) изрядный процент времени будет уходить на то, чтобы побороть свое эротическое к ней отношение. Кстати, все офисные time killer-ы вроде блогов, форумов, YouTube и пр. попадают в эту категорию. За исключением дартса и турника – это совсем другое дело.

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

Причем, когда я называю свой срок, я уже произвожу такое умножение (на коэффициент в диапазоне от 2 до 4-х), но все равно ошибаюсь. А взять больший коэффициент не позволяет (пока?) все тоже самомнение: “Ну как же! Да не может быть, чтобы вместо одной недели потребовалось пять-шесть недель!” :)

17 комментариев:

  1. Точно рссчитать срок можно только в одном случае, если такая же работа уже делалась. "Такая же" подразумевает в точности то же самое, в том же контексте, теми же средствами, теми же людьми и будет делаться точно так же. И желательно что бы это делалось несколько раз. Собственно это уже не рассчет, а просто озвучивание предыдущего результата.
    В разработке ПО "такой же" работы никогда не бывает (если оно точно то же, то просто возьми старый код).
    В большинстве отраслей связанных с материальным производством как раз бывает практичски всегда "точно такая же" работа - сколько займёт сделать ещё один тысячный камаз?
    Тупые менеджеры не понимают отличия, и пытаются распространить правила, применимые к материальному производству, на не материальное.

    ОтветитьУдалить
  2. В большинстве отраслей связанных с материальным производством как раз бывает практичски всегда "точно такая же" работа - сколько займёт сделать ещё один тысячный камаз?

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

    В программировании такие вещи так же крайне редко встречаюся.

    ОтветитьУдалить
  3. > А еще там есть такая штука (актуально при ремонтах, которые так же отличаются индивидуальностью) -- засечка времени на одну операцию и экстраполяция результата.

    Это фактически "такая же" работа. Сделали метр, ещё метр, дальше можем предсказывать. А разработке ПО такие вещи не то, что редко, а вообще не встречаются. Что-либо будучи однажды создано может быть мгновенно раскопировано произвольное число раз.

    ОтветитьУдалить
  4. Ну так и есть. Из-за чего и наблюдается интересный эффект. Начинается ремонт и сразу не предскажешь, сколько времени он займет (так же, как и программный проект). Но потом, по мере продвижения работ результаты замеров позволяют предсказывать более-менее точные сроки окончания. Как раз из-за повторяемости и одинаковости действий. А в программном проекте даже после его начала очень сложно расчитывать на то, что проект будет развиваться с такой же скоростью и дальше -- скорее наоборот.

    ОтветитьУдалить
  5. сколько времени займет проектирование, уяснение требований заказчика и поиск подводных камней (типа "лицензия может быть не в началае"),действительно трудно оценить, но кодирование, вероятно, должно поддаваться оценке -- там именно повторяющася работа

    ОтветитьУдалить
  6. @имя: я не считаю кодирование повторяющейся операцией. Тем более, что кодирование занимает вовсе не самый большой процент времени разработки. Нужно еще помнить про отладку и тестирование. По хорошему, кодирование и тестирование должны идти вместе, но тогда и скорость кодирования будет очень сильно варьироваться.

    ОтветитьУдалить
  7. Просто программирование - это не производство, а проектирование. Следовательно, здесь не применимы производственные методы. Надо применять проектное планирование. Ты же читал "Оружие победы" Грабина - не зря описанные там проблемы/успехи/способы работы так узнаваемы. Если помнишь, Грабин уделил некоторое внимание "отладке" (чисто конструкторский термин!) - насколько она важна в проектировании и сколько времени она может занять. Ничто не ново под луной, одним словом. Все проблемы идут от решения проблем неверными методами.

    ОтветитьУдалить
  8. @CrystaX: как я понимаю, проблема здесь, по сути, одна. Хотя и в разных проявлениях:
    - для проекта важно в самом начале определить его длительность. Чем точнее, тем лучше;
    - поэтому программисты вынуждены давать такие оценки. Ну или подгонять их под ожидания заказчика/обещания руководства;
    - оценка программиста не может быть точной в силу озвученных здесь обстоятельств;
    - затем никто не занимается пересмотром сроков проекта. Изначально полученная неточная оценка принимается за цель.

    Вспоминается история про SAS (http://www.business-magazine.ru/mech_new/experience/pub330855): "Мы никогда не анонсируем заблаговременно дату поставок наших продуктов, если точно не знаем сроков завершения всех работ. Изо дня в день в отделе тестирования мы вычищаем «баги» и делаем это до тех пор, пока количество вновь обнаруженных ошибок не снижается практически до нуля. Только после этого наши продукты попадают к нашим клиентам" Блин, внушаить! Но далеко не всегда такие вещи возможны даже при выпуске собственного продукта, не говоря уже про заказной софт.

    ОтветитьУдалить
  9. Так вот именно в этом и есть корень проблемы: "Изначально полученная неточная оценка принимается за цель". Проектное планирование отличает адаптивность планов. При этом все сроки - это всего лишь ограничение сверху, которое означает необходимость втиснуться, а если не получилось - менять сроки или, если это невозможно, жертвовать частями проекта. В этом и есть отличие проектирования от производства. На производстве вылет за рамки сроков на 20% - ЧП, в проектной деятельности - высоковероятное явление. Т.к. в отличие от производства, здесь иной критерий качества - не максимальная идентичность изделий, а решение проблемы в заданных рамках.

    ОтветитьУдалить
  10. > На производстве вылет за рамки сроков на 20% - ЧП, в проектной деятельности - высоковероятное явление.

    Иногда мне кажется, что чем выше начальство, тем меньше оно это понимает.

    ОтветитьУдалить
  11. > Тем более, что кодирование занимает вовсе не самый большой процент времени разработки.

    Я хотел это написать, но подумал, что это очевидно.

    Вообще мы что обсуждаем? 1. обоснованность действия менеджеров в разрезе "как оно вообще по отрасли" или 2.как можно оптимизировать и ускорить рабочий процесс?

    Насчет 1 -- это правильно, чтобы в случае зарвавшихся менеджеров полностью отдать им руль (а возможно еще и устроить "делаю только то, что вы указали мне ПИСЬМЕННО"). Но мне это в общем-то неинтересно (представляю, как менеджер вместо оптимизации ассемблерного кода говорит процессору "работай быстрее, падла, а то напряжение питания понижу!!!" :-)

    Мне намного интереснее обсудить 2. То есть возможные организационные *оптимизации* труда программистов.

    Если тебе это интересно, то вот вопрос: а когда вдруг кодирование становится непредсказуемой работой? Единственный известный мне случай -- неполное знание языка/плохой язык, например, для меня писание bat/cmd файлов.

    ОтветитьУдалить
  12. @имя:

    >Вообще мы что обсуждаем?

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

    >Мне намного интереснее обсудить 2. То есть возможные организационные *оптимизации* труда программистов.

    Да, это интересная тема. Но в комментарий ее не засунуть, поэтому я постараюсь посвятить ей отдельный пост.

    >Если тебе это интересно, то вот вопрос: а когда вдруг кодирование становится непредсказуемой работой?

    Навскидку вспоминаются три ситуации:

    1. Приходится иметь дело с новой предметной областью (особенно когда с компьютера нужно управлять новым железом). Тогда на каждом шагу обнаруживаются какие-то сюрпризы, с которыми приходится разбираться.

    2. Когда идет инкрементальная разработка с частой передачей версий заказчику и с хорошей обратной связью. В понедельник отдаешь версию 1.5.10, только-только приступаешь с версии 1.5.11, а во вторник-среду от заказчика поступают предложения/замечания... Приходится делать версию 1.5.10.1, потом 1.5.10.2, а работа над 1.5.11 затягивается.

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

    ОтветитьУдалить
  13. Этот комментарий был удален автором.

    ОтветитьУдалить
  14. Приятно почитать взгляд с вашей колокольни :-)

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

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

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

    ОтветитьУдалить
  15. @Lamer:

    >IMHO, тут надо учиться отдельно двум вещам - отдельно оценке и отдельно программированию.

    Я бы еще одну вещь добавил. Нужно учиться работать без противостояния "хороший программист - плохой менеджер" или "плохой программист - успешный менеджер (tm)". Ведь цель у всех одна -- успешный проект. Зона обязанностей и ответственности разная только.

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

    ОтветитьУдалить