Utrzymanie programu w głowie

Sierpień 2007

Dobry programista intensywnie pracujący nad własnym kodem potrafi utrzymać go w umyśle w taki sam sposób, w jaki matematyk utrzymuje problem, nad którym pracuje. Matematycy nie odpowiadają na pytania, rozwiązując je na papierze w sposób, w jaki uczono dzieci w szkole. Robią więcej w swoich głowach: starają się zrozumieć przestrzeń problemową na tyle dobrze, aby móc ją obejść, tak jak można obejść pamięć domu, w którym się dorastało. W najlepszym wydaniu programowanie jest tym samym. Trzymasz cały program w głowie i możesz nim manipulować według własnego uznania.

Jest to szczególnie cenne na początku projektu, ponieważ początkowo najważniejszą rzeczą jest możliwość zmiany tego, co robisz. Nie tylko rozwiązania problemu w inny sposób, ale zmiany problemu, który rozwiązujesz.

Twój kod to twoje zrozumienie problemu, który badasz. Więc dopiero gdy masz swój kod w głowie, naprawdę rozumiesz problem.

Niełatwo jest umieścić program w głowie. Jeśli opuścisz projekt na kilka miesięcy, powrót do niego i ponowne jego zrozumienie może zająć dni. Nawet gdy aktywnie pracujesz nad programem, za każdym razem, gdy zaczynasz pracę danego dnia, może to zająć pół godziny, aby załadować go do głowy. A to w najlepszym przypadku. Zwykli programiści pracujący w typowych warunkach biurowych nigdy nie wchodzą w ten tryb. Lub, mówiąc bardziej dramatycznie, zwykli programiści pracujący w typowych warunkach biurowych nigdy tak naprawdę nie rozumieją problemów, które rozwiązują.

Nawet najlepsi programiści nie zawsze mają cały program, nad którym pracują, załadowany do głowy. Ale są rzeczy, które możesz zrobić, aby sobie pomóc:

  1. Unikaj rozpraszaczy. Rozpraszacze są złe dla wielu rodzajów pracy, ale szczególnie złe dla programowania, ponieważ programiści mają tendencję do działania na granicy szczegółów, które są w stanie obsłużyć.

    Niebezpieczeństwo rozproszenia zależy nie od jego długości, ale od tego, jak bardzo ono miesza w twoim mózgu. Programista może wyjść z biura i zjeść kanapkę, nie tracąc kodu z głowy. Ale niewłaściwy rodzaj przerwania może wyczyścić mózg w 30 sekund.

    Co dziwne, zaplanowane rozpraszacze mogą być gorsze niż nieplanowane. Jeśli wiesz, że masz spotkanie za godzinę, nawet nie zaczynasz pracować nad czymś trudnym.

  2. Pracuj w długich sesjach. Ponieważ za każdym razem, gdy zaczynasz pracę nad programem, ponosisz stały koszt, bardziej efektywne jest pracowanie w kilku długich sesjach niż w wielu krótkich. Oczywiście przyjdzie moment, kiedy staniesz się głupi z powodu zmęczenia. To różni się w zależności od osoby. Słyszałem o ludziach kodujących przez 36 godzin z rzędu, ale najwięcej, co mi się udało, to około 18, a ja pracuję najlepiej w blokach nie dłuższych niż 12.

    Optimum to nie jest limit, który możesz fizycznie znieść. Przerwanie projektu ma zarówno zalety, jak i koszty. Czasami po odpoczynku wracając do problemu, okazuje się, że twój podświadomy umysł zostawił dla ciebie odpowiedź.

  3. Używaj zwięzłych języków. Bardziej potężne języki programowania sprawiają, że programy są krótsze. A programiści wydają się myśleć o programach przynajmniej częściowo w języku, którego używają do ich pisania. Im bardziej zwięzły język, tym krótszy program i tym łatwiej go załadować i utrzymać w głowie.

    Możesz wzmocnić efekt potężnego języka, używając stylu zwanego programowaniem od dołu do góry (bottom-up programming), gdzie piszesz programy w wielu warstwach, dolne działają jako języki programowania dla tych powyżej. Jeśli zrobisz to dobrze, musisz tylko utrzymać najwyższą warstwę w głowie.

  4. Ciągle przepisuj swój program. Przepisywanie programu często prowadzi do czystszego projektu. Ale miałoby to zalety nawet wtedy, gdyby nie miało: aby przepisać program, musisz go całkowicie zrozumieć, więc nie ma lepszego sposobu, aby go załadować do głowy.

  5. Pisz czytelny kod. Wszyscy programiści wiedzą, że dobrze jest pisać czytelny kod. Ale ty sam jesteś najważniejszym czytelnikiem. Zwłaszcza na początku; prototyp to rozmowa z samym sobą. A pisząc dla siebie, masz inne priorytety. Jeśli piszesz dla innych ludzi, możesz nie chcieć, aby kod był zbyt gęsty. Niektóre części programu mogą być najłatwiejsze do odczytania, jeśli rozłożysz rzeczy, jak w podręczniku wprowadzającym. Natomiast jeśli piszesz kod, aby łatwo go załadować do głowy, najlepiej postawić na zwięzłość.

  6. Pracuj w małych grupach. Kiedy manipulujesz programem w głowie, twój wzrok zazwyczaj zatrzymuje się na krawędzi kodu, który posiadasz. Innych części nie rozumiesz tak dobrze, a co ważniejsze, nie możesz z nimi robić swobodnych ruchów. Więc im mniejsza liczba programistów, tym bardziej kompletna może być mutacja projektu. Jeśli jest tylko jeden programista, jak często bywa na początku, możesz przeprowadzać wszechstronne przeprojektowania.

  7. Nie pozwól, aby wiele osób edytowało ten sam fragment kodu. Nigdy nie rozumiesz kodu innych ludzi tak dobrze jak swojego własnego. Bez względu na to, jak dokładnie go przeczytałeś, tylko go przeczytałeś, nie napisałeś go. Więc jeśli fragment kodu jest napisany przez wielu autorów, żaden z nich nie rozumie go tak dobrze, jak zrobiłby to jeden autor.

    I oczywiście nie możesz bezpiecznie przeprojektować czegoś, nad czym pracują inni ludzie. Nie chodzi tylko o to, że musiałbyś prosić o pozwolenie. Nawet nie pozwolisz sobie na takie myśli. Przeprojektowanie kodu z wieloma autorami jest jak zmiana praw; przeprojektowanie kodu, który kontrolujesz sam, jest jak zobaczenie innej interpretacji niejednoznacznego obrazu.

    Jeśli chcesz zaangażować kilka osób w projekt, podziel go na komponenty i przekaż każdemu po jednej osobie.

  8. Zacznij od małego. Program staje się łatwiejszy do utrzymania w głowie, gdy się z nim zapoznajesz. Możesz traktować części jako czarne skrzynki, gdy poczujesz się pewnie, że je w pełni zbadałeś. Ale kiedy po raz pierwszy zaczynasz pracować nad projektem, jesteś zmuszony widzieć wszystko. Jeśli zaczniesz od zbyt dużego problemu, możesz nigdy nie być w stanie go objąć. Więc jeśli musisz napisać duży, złożony program, najlepszym sposobem na rozpoczęcie może nie być napisanie specyfikacji, ale napisanie prototypu, który rozwiązuje podzbiór problemu. Jakiekolwiek by nie były zalety planowania, często są one przyćmione przez zalety możliwości utrzymania programu w głowie.

Uderzające jest to, jak często programiści przypadkowo trafiają we wszystkie osiem punktów. Ktoś ma pomysł na nowy projekt, ale ponieważ nie jest oficjalnie zatwierdzony, musi go realizować w wolnym czasie – co okazuje się bardziej produktywne, ponieważ nie ma rozpraszaczy. Napędzany entuzjazmem do nowego projektu, pracuje nad nim przez wiele godzin z rzędu. Ponieważ jest to początkowo tylko eksperyment, zamiast języka „produkcyjnego” używa zwykłego języka „skryptowego” – który w rzeczywistości jest znacznie potężniejszy. Wielokrotnie przepisuje program; nie byłoby to uzasadnione w oficjalnym projekcie, ale jest to praca z miłości i chce, aby był doskonały. A ponieważ nikt inny go nie zobaczy, pomija wszelkie komentarze poza tymi typu „notatka dla siebie”. Pracuje w małej grupie z konieczności, ponieważ albo jeszcze nikomu nie powiedział o tym pomyśle, albo wydaje się on tak nieobiecujący, że nikt inny nie może nad nim pracować. Nawet jeśli jest grupa, nie mogliby mieć wielu osób edytujących ten sam kod, ponieważ zmienia się on zbyt szybko, aby było to możliwe. A projekt zaczyna się od małego, ponieważ pomysł jest początkowo mały; ma tylko jakiś fajny hack, który chce wypróbować.

Jeszcze bardziej uderzające jest to, ile oficjalnie zatwierdzonych projektów robi wszystko źle. W rzeczywistości, jeśli spojrzeć na sposób, w jaki oprogramowanie jest pisane w większości organizacji, wygląda to prawie tak, jakby celowo próbowali robić rzeczy źle. W pewnym sensie tak jest. Jedną z definiujących cech organizacji od zawsze było traktowanie jednostek jako wymiennych części. Sprawdza się to dobrze w przypadku bardziej równoległych zadań, takich jak prowadzenie wojen. Przez większość historii dobrze wyszkolona armia zawodowych żołnierzy mogła pokonać armię indywidualnych wojowników, bez względu na ich waleczność. Ale posiadanie pomysłów nie jest zbyt równoległe. A tym właśnie są programy: pomysłami.

Nie tylko to, że organizacje nie lubią polegać na indywidualnym geniuszu, to tautologia. To część definicji organizacji – nie polegać. Przynajmniej naszej obecnej koncepcji organizacji.

Może moglibyśmy zdefiniować nowy rodzaj organizacji, który łączyłby wysiłki jednostek bez wymagania, aby były wymienne. Prawdopodobnie rynek jest taką formą organizacji, chociaż dokładniejsze może być opisanie rynku jako przypadku zdegenerowanego – jako tego, co otrzymujesz domyślnie, gdy organizacja nie jest możliwa.

Prawdopodobnie najlepsze, co możemy zrobić, to jakiś hack, jak sprawić, by programistyczne części organizacji działały inaczej niż reszta. Być może optymalnym rozwiązaniem jest to, aby duże firmy nawet nie próbowały rozwijać pomysłów wewnętrznie, ale po prostu je kupowały. Ale niezależnie od tego, jakie okaże się rozwiązanie, pierwszym krokiem jest uświadomienie sobie problemu. W samym zwrocie „firma software’owa” tkwi sprzeczność. Oba słowa ciągną w przeciwnych kierunkach. Każdy dobry programista w dużej organizacji będzie z nią w konflikcie, ponieważ organizacje są zaprojektowane tak, aby zapobiegać temu, do czego dążą programiści.

Dobrzy programiści i tak udaje im się wiele osiągnąć. Ale często wymaga to niemal aktu buntu przeciwko organizacjom, które ich zatrudniają. Być może pomoże, jeśli więcej osób zrozumie, że sposób, w jaki zachowują się programiści, jest podyktowany wymaganiami pracy, którą wykonują. Nie dlatego, że są nieodpowiedzialni, pracują w długich seriach, podczas których olewają wszystkie inne obowiązki, od razu zabierają się do programowania zamiast najpierw pisać specyfikacje i przepisują działający kod. Nie dlatego, że są nieprzyjaźni, że wolą pracować sami lub warczą na ludzi, którzy zaglądają przez drzwi, żeby się przywitać. Ta pozornie przypadkowa kolekcja irytujących nawyków ma jedno wyjaśnienie: potęgę utrzymania programu w głowie.

Niezależnie od tego, czy zrozumienie tego pomoże dużym organizacjom, z pewnością pomoże ich konkurentom. Najsłabszym punktem dużych firm jest to, że nie pozwalają one poszczególnym programistom na świetną pracę. Więc jeśli jesteś małym startupem, to jest miejsce, aby ich zaatakować. Podejmuj się rozwiązywania problemów, które muszą być rozwiązane w jednym wielkim mózgu.

Dzięki Samowi Altmanowi, Davidowi Greenspanowi, Aaronowi Ibę, Jessice Livingston, Robertowi Morrisowi, Peterowi Norvigowi, Lisie Randall, Emmettowi Shearowi, Siergiejowi Tsarevowi i Stephenowi Wolframowi za przeczytanie wersji roboczych tego tekstu.