the mythical man-month 1 program -> programming system (interfaces, system integration) program -> programming product (generalization, testing, docs, maintenance) - multiplies effort by three times (p. 5) this is why amateurs seem to have more success than companies 2 scheduling problems a) optimism - belief that "all will go well" - inconsistencies/incompleteness of ideas only becomes clear during implementation - computers are a tractable (flexible) medium, so the tendency is to assume there will be fewer implementation problems - systems have many parts, so the chance that *everything* goes well is very small b) the man-month - cost varies as the number of men * the number of months - progress does *not* - men and months are only interchangeable if a task is perfectly partitionable (i.e. there is no communication between subtasks) -> this is especially *not* true for systems programming (p. 16) - perfectly non-partitionable -> adding more men saves no time (p. 17) ex: sequential tasks like debugging - communication brings at least slightly worse results than perfect partitioning (p. 18), ex: training issues - complex intercommunications mean communication grows O(n^2)!! (p. 19) -> this tends to happen with systems programming! c) testing - tendency to underschedule, number of bugs is underestimated - brooks recommends 1/2 the schedule for testing most don't schedule this much, but spend it anyway. - especially important is the system test (entire system as one) -> can sneak up, causing secondary costs (when things depend on the product being released) d) "rush" estimation of time required - many will estimate low to look good on paper e) regenerative schedule disaster (p. 22-26) basically, if a project is behind schedule, adding more men to equalize the available man-hours with the required man-hours *does not work*. 4 conceptual integrity - better to omit features and have a consistent design than to include uncoordinated features optimize ratio of function to conceptual complexity optimize ratio of usefulness/features to time needed for training or searching manuals best to have one person, or a few people in agreement with resonating minds, to write the design spec. design spec of user interface (manuals) is the "architecture" (what happens) "implementation" is how it happens (underlying code) aristocracy vs. democracy need aristocracy for consistency and focus a constrained design can actually often improve the resulting implementation divide tasks between architecture, implementation, and realization (hardware) 5 second system effect in an architect's first system, much caution is exercised. frills are punted. the second system is the most dangerous, because the architect thinks he knows what he's doing, and so he adds frills indiscriminately. in later systems, he has more experience and will see larger trends in design methods that will help him avoid problems. in a second system, an architect will also often refine techniques that are actually obsolete due to changes in design assumptions. an architect should therefore be extra-disciplined and exercise caution with his second system. 8 estimating programming time is *non-linear* with code size experimental data indicates: - effort = O(n^1.5), where n = the number of instructions - actual productivity = half the time spent "working" (due to system downtime, personal time, etc.) - productivity increases when higher-level languages are used (addresses conceptual complexity) 11 a "pilot plant" is a test system used to test scaling a system up. a first try at a design can tend to be: - too slow - too big - awkward to use furthermore, the first try is almost always thrown away, so plan to do so. avoid schedules that require shipping the first thing built (disastrous). greater truth: change is inescapable - user need and user perception change with time and with program use - design and implementation evolve with time and technology plan for change: 6.033 helps - modularity - interfaces - documentation - versioning - use a high level language when possible (abstraction) it's hard to document a system when you know it'll change, but do it anyway. make your management structure flexible - train managers on technical aspects - train senior techs on management issues - avoid social obstacles that make people feel bad (e.g. "i don't want to sink to the level of a coder.") structure raises so that management is not paid more than programmers (does this happen in real life? ;) the cost of system maintenance is 40% of the cost of its development, or more when there is a large user base. in a new release, old bugs reappear. as they are fixed, there is a period of calm. then, more complex bugs are found as users get more sophisticated, and stretch the system to its limits. fixing a bug has a 20-50% chance of causing at least one new bug: - propagation effects - repairer may not be original author, causing errors - regression testing (rerunning all test cases) is costly, and often skipped fix: design system to show side effects easily - fewer programmers - fewer interfaces as a program's life progresses, more time is spent on just the bugs from bug fixes. more modules -> more complexity -> more problems. eventually it is best to redesign the program entirely!