Zarządzanie projektami, zespołem i analiza IT

Zarządzanie projektami

7 kluczowych cech dobrego programisty

W tym wpisie poruszę temat umiejętności miękkich u developerów. Według mnie ten aspekt jest często zaniedbywany w rozwoju kariery, a bez niego nie można określić się kompletnym programistą. Opiszę 6 wybranych cech, które definiują „dobrego” developera, tymi wartościami kieruję się rekrutując do fresh-apps.com. Nie było prosto ubrać w słowa cechy, które miałem w głowie – więc jako nazwy nagłówków dałem wspólny mianownik moich myśli, które szerzej opisałem w akapitach.

1. odpowiedzialność

Musisz brać odpowiedzialność za swój kod. Kropka. Wiąże się to bezpośrednio z dokładnością. Oddając swój kod, nie możesz być pewnym jego działania tylko pobieżnie – sprawdzając podstawowe scenariusze/parametry. Musi być gruntownie przetestowany, nie możesz liczyć, że „w razie czego wróci ticket i poprawię”. W ten sposób marnujesz czas swojego zespołu. Pisanie dobrej jakości kodu zależy właśnie do ciebie i powinieneś to zrealizować najlepiej jak potrafisz. Nie dostajesz wypłaty za poprawianie swoich błędów tylko pisaniu niezawodnego oprogramowania. Często frustrowałem się dostając funkcjonalność „do przeklikania” gdy znajdowałem w niej bugi w pierwszych minutach testowania. Byłem pewny, że wynikają z braku dokładności jego twórcy. Nie mówię tutaj o błędach, które ciężko wychwycić programiście – np. błędy bezpieczeństwa. Mam na myśli głównie brak walidacji danych, spójności między modułami i poprawności dla krańcowych parametrów.
Bardzo powiązanym zjawiskiem, które często obserwuje jest sytuacja „ale to nie moja wina!”. Najczęstszymi winowajcami jest GIT, SVN i osoba, która testuje bo przecież „u mnie działa” 😉 Zdaję sobie sprawę, że prawa murphy’ego działają i często nie jesteśmy w stanie przewidzieć zachowań komputera, ale większości z nich możemy zapobiec pisząc sumienny kod. Znasz uczucie, gdy testując kod modlisz się, żeby ten zestaw parametrów zadziałał bo będziesz mógł zaznaczyć zadanie jako wykonane? Też je znam, na szczęście szybko się go wyzbyłem. Powinieneś oddać kod, gdy brak Ci pomysłu na podanie parametrów, które nie zadziałają, a nie gdy znajdziesz jedyne, które działają 🙂 W skrócie, dobrego programistę określa: dokładność, dokładność i jeszcze raz odpowiedzialność!

Krótki przykład wyjaśniający dlaczego droższe jest tańsze na podstawie pracy developera vs odpowiedzialnego developera.

Developer A : zarabia kwotę X (przyjmijmy, że x=100%).
Developer B: zarabia kwotę Y (y = x+20%, zarabia o 20% więcej niż A).

Obaj developerzy realizują pewne zadanie przez 1 dzień. Obaj twierdzą, że zadanie jest wykonane. Do developera A jednak wracają bugi, które musi naprawić, a ich poprawa zajmuje mu kolejne pół dnia. W ogólnym rozrachunku developera A kosztuje nas 150% bazowej pensji (podczas gdy developer B  – 120%). Wybierając developera B oszczędzamy pieniądze i realizujemy projekt na czas. W przypadku developera A jest drożej i dłużej. Dobry przykład, który pokazuje jak odpowiedzialność (cechy charakteru) wpływa na wydajność w pracy.


Bezpieczna umowa na Wykonanie Projektu IT


2. samodzielność w rozwiązywaniu problemów

Bądź samodzielny. Podczas tworzenia oprogramowania będziesz spotykał się z mniejszymi i większymi problemami – rozwiązuj je. Zdarza się, że developerzy nie podchodzą do rozwiązywania problemów aktywnie, a jedynie informują o zaistniałym problemie i oczekują, że ktoś im poda rozwiązanie na tacy. Programista po zdiagnozowaniu problemu powinien wrócić z rozwiązaniem (lub ewentualnie z propozycjami rozwiązania – jeśli nie jest pewien, które wybrać). Działając w ten sposób wykazujemy inicjatywę, rozwijamy naszą kreatywność i zdolność rozwiązywania problemów (same plusy 😉 ). Spróbuj w swoim słowniku każde „nie wiem” zamienić na „dowiem się”. Mówiąc „nie wiem” – stwierdzasz to, że nie jesteś kompetentny w danym temacie i nie podejmujesz działań, natomiast mówiąc „dowiem się” – przyjmujesz pozycję aktywną, bo komunikujesz, że wykonasz akcje by zgłębić swoją wiedzę. Nie skupiasz się na obecnym stanie rzeczy (niewiedzy) tylko na działaniach prowadzącym do rozwiązania problemu. Doprowadzaj swoje zadania do końca mimo problemów, które wystąpią po drodze. Będąc samodzielnym w tym całym procesie rozwijasz się, ponieważ podnosisz sobie coraz wyżej poprzeczkę – stawiając czoła coraz trudniejszym problemom.

3. bądź określony

Musisz znać swoje mocne i słabe strony. Powinieneś wiedzieć w jakich technologiach jesteś dobry, a w których się jeszcze szkolisz. Do dziś zastanawiam się nad sensem wpisywania turbo pascala w CV, ale o dobrym CV kiedy indziej. Powinieneś ocenić, które z Twoich cech są tzw. „sprzedawalne” – czyli za które ktoś ci jest w stanie zapłacić. Turbo Pascal przyda się jedynie, gdy szukasz pracy jako programista w TP lub Delphi, w innym przypadku prawdopodobnie ci nie pomoże. Kiedy ktoś się ciebie pyta, czy znasz framework xyz, to uwierz mi, że go nie znasz, jeśli założyłeś w nim jeden projekt na studiach 3 lata temu. Jeśli mówisz, że znasz język programowania/framework bo napisałeś w nim Hello World – dajesz sprzeczny komunikat ponieważ prawdopodobnie nie dasz sobie rady z tak małą wiedzą w środowisku produkcyjnym, a to zazwyczaj ma na myśli pytający. W ten sposób doprowadzasz do sytuacji, gdy trzeba weryfikować informacje wychodzące od ciebie – jaskrawy przykład, ale mam nadzieję, że wiesz co mam na myśli. Warto wiedzieć w jakim punkcie się jest i do jakiego się zmierza. Na początku kariery jest to trudne, ale ważne by obiektywnie ocenić swoje umiejętności bez przesady w jedną, ani drugą stronę. Nie musisz być człowiekiem renesansu, nie musisz znać wszystkich technologii – wystarczy, że będziesz znał te, w które zadeklarujesz, że znasz. W ten sposób przestaniesz być niewiadomą, a project manager będzie w stanie przypisać cię do odpowiedniego projektu bez rozczarowań dla obu stron. Wpłynie to również na większą terminowość realizacji projektów – bo jeśli project manager zna twój faktyczny stan wiedzy programistów może założyć odpowiedni margines.

4. nie bój się przyznać do niewiedzy

Nie możesz się bać przyznać, że czegoś nie wiesz lub nie rozumiesz. Zdarza się, że tłumacząc coś developerom widzę na ich twarzy brak zrozumienia gdy kiwają głowami, że wszystko jest jasne. Staram się tłumaczyć do tego momentu, aż sam mam pewność, że druga strona mnie rozumie – niektórzy są jednak naprawdę dobrzy w udawaniu, że rozumieją i udaje im się mnie przechytrzyć. Jeśli programista nie rozumie celu i zakresu swoich prac są małe szanse, że wykona zadanie poprawnie za pierwszym razem. Każde regresje/poprawki wynikające z braku zrozumienia zajmują nam czas – zamiast iść do przodu, tkwimy w miejscu. Zazwyczaj po każdej iteracji poprawek następują pytania ze strony developera – z którąś z tych iteracji w końcu temat zostanie zrozumiany a task poprawnie wykonany. Możemy zaoszczędzić sobie czasu i przyznać się do braku zrozumienia podczas pierwszego tlumaczenia zamiast np czwartego 😉 Oczywiście pomijam tutaj kwestie, gdy ktoś może nie mieć daru dydaktycznego i źle tłumaczyć co ma na myśli lub pisać takie kryterium akceptacji, które po kilku dniach są nie jasne nawet dla autora. Podczas studiów gdy byłem na praktykach, project manager tłumaczył mi pewne zadanie, na końcu zapytał „masz jakieś pytania?”. Odpowiedziałem, że „nie mam pytań” po czym usłyszałem odpowiedź: „oj, to nie dobrze!”. Ta rozmowa utkwiła mi w pamięci, a zrozumiałem ją dopiero gdy zacząłem pracować. Moim zdaniem powiedzenie „nie ma głupich pytań, są tylko głupie odpowiedzi” ma ogromny sens – pytanie rozwija poprzez wiedzę zdobytą z odpowiedzi.


Wideo: Wycena Projektu IT od A – Z


5. pewność siebie

Musisz być pewny siebie. Często zadając pytanie „czy wszystko działa?”, słyszę odpowiedź „chyba działa”. Większość odpowiedzi na pytania możemy sprowadzić do wartości 0 i 1 – albo kod działa, albo nie. Nie ma wersji pomiędzy. Jeśli nie wiesz czy Twój kod działa – odpowiedz, że nie testowałeś i nie możesz potwierdzić. Chodzi tutaj o komunikat – druga strona musi wiedzieć jaki jest faktyczny stan rzeczy bo „chyba działa” mówi niewiele.

W psychologii istnieje ciekawe zjawisko, które nazywa się efektem Krugera-Dunninga – ja obserwuje je bardzo często. W wielkim skrócie, chodzi o to, że osoby, które są mało kompetentne w danym temacie – czują się w nim bardzo pewnie. Natomiast osoby bardzo kompetentne w danym temacie – czują się mniej pewnie siebie. Wynika to z etapów kompetencji:

  • nieświadoma niekompetencja – jest wtedy, gdy nie wiesz czego nie wiesz. Ja jestem nieświadomie niekompetentny w zakresie budowania rakiet – nie mam pojęcia co muszę wiedzieć by być osobą kompetentną. W skrócie : nie wiem, co powinienem wiedzieć. Np student pierwszego roku, nie zdaje sobie sprawy z zakresu materiału, którego musi się nauczyć.
  • świadoma niekompetencja – etap, gdy dowiadujemy się co musimy wiedzieć by być kompetentnym w danym temacie, jednak nadal tej wiedzy nie mamy i pozostajemy niekompetentni. Jest to np student podczas pierwszej sesji, gdy poznał ogrom materiału i dowiedział się co musi umieć, ale niestety zrobił to wieczór przed egzaminem i nie zdąży wykuć. Jest to również developer, który przeczytał książkę o języku programowania i dowiedział się ile rzeczy musi się jeszcze nauczyć. W skrócie: wiem, że nic nie wiem 😉
  • nieświadoma kompetencja – etap gdy staliśmy się kompetentni, ale nie zdajemy sobie z tego sprawy. Często na tym etapie są absolwenci uczelni – mają wiedzę by wykonywać zawód, ale nie są jeszcze na tyle pewni siebie by być tego świadomym. Na tym etapie najczęściej mamy umiejętności twarde by wykonywać czynność, jednak brak nam umiejętności miękkich.
  • świadoma kompetencja – ten etap następuje po nieświadomej kompetencji. Uświadamiamy sobie, że jesteśmy w czymś naprawdę dobrzy. Czujemy się kompetentni w tym temacie. Mamy pełny zestaw umiejętności miękkich i twardych. Jesteśmy ekspertami w danej dziedzinie.

Ważną kwestią z punktu widzenia developera jest dążyć do ostatniego etapu oraz mieć odpowiednią świadomość w którym etapie jesteśmy z daną technologią. Nie nazywaj się ekspertem jeśli nie masz świadomej kompetencji. Nie nazywaj się juniorem jeśli masz nieświadomą kompetencję. Wiąże się to bezpośrednio z pewnością siebie oraz określeniem siebie (poprzednie akapity). Najważniejszą rzeczą jest więc określenie aktualnego stanu naszej wiedzy z konkretnej dziedziny, wtedy wiemy gdzie jesteśmy i możemy określić kierunek na przód. Jeśli tego nie zrobimy to może zdarzyć się, że wiemy wszystko i zarazem nic ponieważ nie umiemy ukierunkować naszego rozwoju. Czasami trafiamy na „człowieka orkiestrę” – zrobi frontend, backend i zaprojektuje interfejs. Nie myl tego proszę z przekrojowością. Przeciwstawne umiejętności są potrzebne np. web developerowi (backend/frontend/grafika) – to nazywa się przekrojowością ponieważ wszystkie elementy są potrzebne do wykonywania profesjonalnie swoich założeń – strony WWW. Natomiast programista C++ jeśli projektuje również layout do strony WWW i konfiguruje serwery – to w większości przypadków, któraś z tych rzeczy jest dobrana „na wyrost”. W takim przypadku tracimy na jakości w wykonaniu zadań przez taką osobę i możemy mieć wcześniej wspomniany przypadek gdy umiemy wszystko i zarazem nic. Właśnie dlatego bardzo ważne jest określenie w którym punkcie jesteśmy i do którego zmierzamy (jak się rozwijamy).
Codziennie podczas rozmowy z ludźmi spotykamy się z różnymi technikami manipulacji – jedni ich używają świadomie, inni nie. Będąc programistą musisz być na tyle pewnym siebie, by nie ulegać naciskom odnośnie wykonywania zadań w nierealnych dla ciebie terminach. Jeśli dostajesz task, na którego wykonanie masz z góry określone ramy czasowe i wiesz, że się nie wyrobisz – powiedz o tym, nie deklaruj, że zdążysz. Możesz powiedzieć, że rozumiesz presję czasu i zrobisz wszystko by zrealizować go w tym terminie, ale nie możesz za to ręczyć. Nie daj zrzucić na siebie odpowiedzialności za wykonanie tasku, którego terminowość jest z góry skazana na porażkę – bądź asertywny, potraf odmówić. Podejmowanie wyzwań jest ciekawe, ale wtedy gdy faktycznie istnieje możliwość ich wypełnienia.

6. nie myśl szablonowo, używaj szablonów

Tytuł jest w pewnym rodzaju grą słów – nie pasowało mi nic innego 😉 Niezwykle istotne jest podeście do zadanego problemu. Należy wybrać odpowiednią metodę rozwiązania – adekwatną do skali problemu. Niestety często można się spotkać z przerostem formy nad treścią, gdy do błahego problemu developer stosuje skompilowane i przede wszystkim pracochłonne rozwiązanie ponieważ chce się czuć „dopieszczony” jako dobry technicznie programista. Wielu developerów ma problem z rozwiązywaniem problemów gdy podany jest im cel zamiast zakresu.

Krótki przykład:
Task z celem: funkcjonalność ma umożliwiać dodanie dwóch liczb z pól A i B. Wynik wyświetlamy w polu C.
Task z zakresem: napisz metodę, która przypiszę do pola C sumę wartości z pól A i B.

Widzisz różnicę? W tasku z celem opisujemy co ma być efektem pracy, natomiast w tasku z zakresem opisujemy co trzeba zrobić. W tasku z celem sam musisz dojść jak rozwiązać problem. Umiejętność rozwiązywania obu typów zadań charakteryzuje dobrego developera – potrafi zrealizować czyjąś koncepcję oraz zaproponować i wdrożyć własne rozwiązanie problemu.
Kolejną rzeczą to „nie wymyślanie koła od nowa” – powtarzane jak mantra, jednak ciągle umyka developerom. Rozwiązania wielu problemów są gotowe, często w postaci bibliotek czy frameworków – wystarczy z nich skorzystać. Przed przystąpieniem do zadania warto zrobić chociaż krótki research istniejących rozwiązań, przeanalizować czy któreś z nich będzie nam przydatne. Budując naszą aplikację klockami z gotowych modułów oszczędzamy czas. Użycie gotowych rozwiązań ma też drugą stronę: w dołączanym kodzie mogą być błędy, kod dołączany może być mało elastyczny w naszym projekcie – jednak w wielu przypadkach możemy to wrzucić w „koszt uzyskania przychodów” 😉 Opisałem to pokrótce w tym wpisie. Podsumowując, nie możesz myśleć szablonowo (stosować jeden typ rozwiązania do każdego problemu), musisz używać szablonów (stosować istniejące rozwiązania, które oszczędzą twój czas).

7. przyjmowanie krytyki

Warto zaznaczyć, że tym akapicie mowa o konstruktywnej krytyce. Jako developer, musisz zaakceptować, że Twój kod będzie miał błędy i nie zawsze będzie idealny. Problem rodzi się wtedy, gdy programista identyfikuje się ze swoim kodem – uważa, że uwagi do kodu dotykają go personalnie. Często powoduje to frustracje i ślepe wypieranie się winy. Jest to błąd w myśleniu, ponieważ pomyłki zdarzają się nawet najlepszym. Tworząc kod musisz przezwyciężyć odruch obronny swojego dzieła i uważnie przyjrzeć się opiniom testerów. Dzięki retrospekcji konstruktywnej krytyki, jesteś w stanie wyciągnąć wnioski, przeanalizować sytuację i stać się lepszym programistą. Niestety nie wszyscy potrafią przyjąć uwagę odnośnie swojej pracy bez wypierania się mówiąc: „It’s not a bug – it’s a feature!”.

57398326

Podsumowując: uwagi dotyczące twojego kodu, nie odnoszą się do ciebie personalnie – więc bez frustracji. Jedynie twój kod może się zdenerwować bo o niego chodzi 😉 Krytykę bierzemy „na klatę” i staramy się nie popełnić drugi raz tego samego błędu. Musisz uświadomić sobie, że nie ma programów bez błędów, są tylko te z nieznalezionymi błędami 😉

Sprawdź jak mogę Ci pomóc osiągnąć Twoje cele 🎯


Podsumowanie

Po napisaniu tego wpisu doszedłem do wniosku, że wyżej wymienione cechy określają nie tyle dobrego developera, ale dobrego pracownika – odniesienie do każdej branży. Do wykonywania każdej czynności potrzebujemy dwóch rodzaju umiejętności – twardych i miękkich. Niezwykle ważne jest by rozwijać je równomiernie – jeśli tak się nie dzieje tracimy na całokształcie. Na co zda ci się perfekcyjny angielski (umiejętność twarda), jeśli będziesz wstydził się rozmawiać w tym języku (brak umiejętności miękkiej)? Z innej strony; na co zda ci się otwarta osobowość do rozmów z obcymi (umiejętność miękka), jeśli nie będziesz znał wystarczającej ilości słówek w obcym języku by się komunikować (brak umiejętności twardej)? Wszystko musi być wyśrodkowane. Nikt nie szuka geniusza, który nie potrafi się komunikować i pracować w zespole, ale z drugiej strony; nikt nie szuka kogoś kto nie jest intelektualnie zdolny do programowania mimo ciekawej osobowości. Moim zdaniem zdecydowanie trudniej jest rozwinąć umiejętności miękkie niż twarde.
Nawet średnio rozgarniętego szympansa można nauczyć pisać sekwencję znaków na konkretne polecenie (praca odtwórcza). Praca odtwórcza ma też miejsce gdy developer nie podchodzi aktywnie do rozwiązywania problemów (poprzednie akapity). Niektóre z szympansów potrafią się podpisać, więc pewnie kwestia czasu jak zaczną programować swoje homepage 😉 Natomiast nauczyć szympansa tego, żeby wziął odpowiedzialność za swój kod oraz wykazał się inwencją twórczą już nie jest tak łatwo 🙂 Jaskrawy przykład, ale mam nadzieję, że wiesz co mam na myśli. Mając developera słabszego technicznie, a odpowiedzialnego i komunikatywnego vs niekomunikatywnego nerda – wybieram pierwszą osobę. Nauka framework, czy nawet języka programowania jest kwestią miesięcy. Obecnie pracodawcy szukają developerów, którzy mają duże podejście biznesowe do swojej pracy. Oprócz tego, że piszą dobry kod, potrafią zaproponować zmiany, znaleźć błąd w logice założeń biznesowych – nie są tylko translatorem tasków na kod. Bądź takim developerem, który myśli podczas pracy. Rozwijaj się technicznie oraz osobowościowo bo jak sam widzisz – jest to bardzo ważne (efekt synergii). Zróbmy sobie wszyscy rachunek sumienia i niech developerzy, będą jeszcze lepszymi developerami. Amen.


Dziękuję, że przeczytałeś ❤️

Pssst... przygotowałem dla Ciebie kilka prezentów - wybierz co Ci się przyda! 👍

11 komentarzy do “7 kluczowych cech dobrego programisty

  • Świetny artykuł – zawiera wiele cennych uwag, do których musiałem dojść sam z latami pracy… 🙂

    Odpowiedz
  • Dobry wpis. Zgadzam się, że pracodawcy nie szukają nerdów, a programistów, którzy będą potrafili porozmawiać nie tylko wew. organizacji, a także poza nią – np. dogadać szczegóły implementowanej funkcjonalności z przedstawicielem klienta. W ostatnim procesie rekrutacyjnym powiedziano mi wręcz, że nie ma problemu ze znalezieniem „klepaczy”, a ze znalezieniem ludzi, którzy posiadają kompetencje miękkie na równie wysokim poziomie jak twarde (na szczęście zaliczono mnie do tego drugiego grona ;)).

    Odpowiedz
  • Bardzo ciekawy artykuł. Jedna tylko uwaga. W jednym punkcie piszesz aby ze słownika usunąć „nie wiem”, gdyż świadczy to o braku kompetencji, a potem piszesz w punkcie 4 „nie bój się przyznać do niewiedzy”… Więc jak to jest? ?

    Odpowiedz
  • Wpis bardzo pomocny, dzięki. Ale hahaha ten mem mnie rozwalił. Szkoda, że niektórzy ludzie nie maja do siebie dystansu.

    Odpowiedz
  • 1. Musi być gruntownie przetestowany, nie możesz liczyć, że “w razie czego wróci ticket i poprawię”.
    Nieprawda – musi być przetestowany w wystarczającym stopniu. Nieraz lepiej szybko napisać trochę kodu niż czekać na 'gruntowanie przetestowany”.
    2. Programista po zdiagnozowaniu problemu powinien wrócić z rozwiązaniem (lub ewentualnie z propozycjami rozwiązania – jeśli nie jest pewien, które wybrać). Działając w ten sposób wykazujemy inicjatywę, rozwijamy naszą kreatywność i zdolność rozwiązywania problemów (same plusy ? ).
    Raczej skonsultować rozwiązanie z innymi członkami zespołu. Szkoda czasu na inicjatywę i kreatywność. Zadanie ma być zrobione szybko. Jako początkujący programista wiele czasu marnowałem na samodzielność.

    Odpowiedz

Dodaj komentarz

Twój adres e-mail nie zostanie opublikowany. Wymagane pola są oznaczone *

Witryna wykorzystuje Akismet, aby ograniczyć spam. Dowiedz się więcej jak przetwarzane są dane komentarzy.