niedziela, 15 maja 2011

Dlaczego się nie uczymy?

"Dlaczego się nie uczymy?" - To tytuł prezentacji, która pojawiła się nie tak dawno an portalu infoq : Why Dont We Learn. Prezenter opisuje mechanizmy jakie towarzyszą zdobywaniu nowych umiejętności a całość zespolona jest w prawdziwą(lub nie) historię z jego życia. Kto chce może obejrzeć prezentacje, natomiast poniżej opiszę 4 etapy zdobywania wiedzy według modelu NLP. Weźmy za przykład naukę umiejętności pisania czystego kodu.


Niekompetencja nieświadoma - nie wiem, że nie wiem


Wyobraź to sobie. Zainteresowałeś się programowaniem jeszcze w szkole średniej gdzie na zajęciach informatyki tworzyłeś pierwsze programy wypisujące po sto razy z rzędu słowo DUPA na ekran monitora. Zauważyłeś, że proces kreacji programu komputerowego generuje pozytywne uczucia, więc poświęcałeś mu coraz więcej i więcej czasu zostawiając w tyle niedzielnych informatyków. Być może zacząłeś pisać programy komercyjnie (cz nielegalnie), poszedłeś na studia gdzie tylko utwierdziłeś się w przekonaniu, że jesteś jednak kimś wybitnym a świadectwem tego były wytworzone serwisy PHP ,które przeplatały linie HTMLa i SQLa ale przecież tak doskonale działały i wyglądały. Innym dziełem był program wisielec napisany w jednej linijce instrukcji "for".


Pewnego dnia, na jeden z tysiąca możliwych sposobów docierają do ciebie informacje burzące twoja homeostazę informatyczną - twój kod jest chu**wy. Takie zdarzenie może przybrać wiele form :

  • wkleiłeś kod na forum i zostałeś zjechany
  • pochwaliłeś się kodem na rozmowie rekrutacyjnej i zostałeś zjechany
  • ktoś odziedziczył twój kod i akcie wybuchu frustracji zjechał cię

Jest to moment krytyczny ponieważ powyższe zdarzenie powoduje aktywację naturalnych mechanizmów obronnych jak "confirmation bias" (nie wiem jakie jest polskie tłumaczenie) czy cały wachlarz samo-oszukiwań zawierający się na "dysonans poznawczy". Opiszę kiedyś bliżej te mechanizmy jakkolwiek w skrócie będzie to wyglądać tak, że twój umysł podświadomy będzie szukał potwierdzenia, że ludzie na forum to debile, osoba rekrutująca na pewno nie zna się na rzeczy bo nie umiała dobrać krawata do swetra zaś osoby które odziedziczyły twój kod to w zasadzie tez debile bo tylko debile nie potrafią operować jednoliterowymi nazwami zmiennych
Gdy Jednak uda ci się opanować chochliki umysłowe dalej jest już z górki.


Niekompetencja świadoma - już wiem, że nie wiem


Wiesz, że twój kod jest niedoskonały ale nie wiesz jaki powinien być. Co robić? Trzeba odnaleźć informację i na ich bazie zdobyć nową wiedzę - nic prostszego. W tym przypadku wpisujesz w google frazę "czysty kod" i chłoniesz wiedzę. Wiedzę można chłonąć w sposób poprawny i niepoprawny (drugi model celebrowany w większości polskich szkół). Problem "Jak się uczyć" to temat rzeka i warto samemu się nim zainteresować traktując jako swoistą meta-wiedzę o dobywaniu nowych umiejętności. Poniżej jeden z masy ciekawych linków :
Dreyfus model of skill acquisition


Kompetencja świadoma - już wiem, że wiem


Trudno stwierdzić, kiedy następuje przejście do tego etapu w przypadku tematu czystego kodu.
Zdobywasz nową wiedzę, uczestniczysz w dyskusjach. Pojawiają się kolejne problemy ale masz wystarczającą bazę wiedzy by znaleźć odpowiedź na większość z nich. Zaczynasz sam optymalizować swoja pracę i zdobytą wiedzę przekazywać innym. W pewnym momencie zauważasz, że kiedy myślałeś o tym czy zamknąłeś drzwi w samochodzie powstał całkiem zgrabny kawałek kodu. Własnie przeszedłeś do ostatniego etapu :


Kompetencja nieświadoma - nie myślę o tym, że wiem

Ten stan łatwiej wytłumaczyć na przykładzie jazdy rowerem czy samochodem. To stan kiedy już nie myślisz w którą stronę idzie dźwignia skrzyni biegów gdy wrzucasz piaty bieg bo całą swoją uwagę skupiasz na bluzganiu kierowcy przed tobą. W tym stanie obydwie te czynności wychodzą ci perfekcyjnie.


Będąc na tym etapie tworzysz dobry kod głównie skupiając się na ogólnej architekturze, ryzykach i problemach które czekają dwa lub trzy kroki przed tobą. I kiedy czujesz w palcach swoje doświadczenie i pływasz w poczuciu mistrzostwa kodu jakiś debil na forum mówi ci, że coś można jeszcze zrobić lepiej....

niedziela, 3 kwietnia 2011

Czy stres może być pomocny?

W literaturze z zakresu psychologii i neurologii można znaleźć opinie, iż krótkotrwały stres jest zjawiskiem pozytywnym. Dopiero gdy towarzyszy nam przez dłuższy czas możemy mówić o jego negatywnych skutkach.


Prawidłowość ta raczej nie sprawdza się w pracy programisty. W trakcie pisania programu musimy zbudować w umyśle dosyć złożone odwzorowanie rozpatrywanej części aplikacji. Z tego co wiem kluczową rolę pełni tutaj hipokamp.


W trakcie reakcji stresowej w naszym ciele wydziela się hormon zwany "kortyzolem" (O tym jak do tego dochodzi można poczytać sobie tutaj --> http://pl.wikipedia.org/wiki/Stres) .Internet mówi , że w roku 2008 zespół prowadzony pod kierownictwem niejakiej Dr Baram
miał dowieść, iż ów kortyzol i inne hormony wydzielane w trakcie stresu upośledzają komunikację neuronów w hipokampie, a przez to zmniejszają efektywność zapamiętywania.


Poziom kortyzolu i inne efekty reakcji na stress powinny być łatwe do zmniejszenia przy pomocy technik relaksacyjnych (chociażby zwolnienie oddechu i odprężenie mięśni). Poniżej jeszcze krótki filmik ilustrujący problem.






Jeśli nie stres to co ma nas motywować do pracy? Być może odpowiedź znajdzie się na wyższym poziomie abstrakcji w szeroko pojętej dziedzinie AUTOMOTYWACJI.Może trzeba poszukać wyższej inspiracji i sensu w tym co tworzymy? A może trzeba przyjrzeć się bliżej co dzieje się w umyśle gracza gdy o 4 nad ranem mówi sobie "jeszcze... tylko... jedna... tura".

niedziela, 20 lutego 2011

Poziomy abstrakcji

Robert C. Martin w swej książce "Czysty kod" wspomina, iż prawidłowo skomponowane funkcje powinny być:
  • małe
  • wykonywać jedną czynność
  • zachowywać jeden poziom abstrakcji


O ile pierwsze dwa punkty łatwo sobie wyobrazić i zaimplementować, o tyle zauważyłem, że ostatni punkt jest nie do końca zrozumiały wśród niektórych programistów.

Aby unaocznić gdzie popełniany jest często błąd użyjmy prostej i każdemu znanej życiowej czynności:

Przepis na jajecznicę

  • Rozpuścić masło na małej patelni
  • Wrzucić na stopione masełko szynkę pokrojoną w małe kwadraciki oraz drobno posiekany szczypiorek
  • rozbić ostrym nożem skorupki jajek i zawartość wylewać na patelnię
  • Dodać trochę soli oraz pieprzu i mieszać, aż do momentu ścięcia się jajek

Przepis jest intuicyjny i raczej nikt nie powinien mieć problemu z jego zrozumieniem. Na tym poziomie abstrakcji wystarczy użyć kilku składników w prosty sposób i już mamy nasza potrawę gotową.

Jednakże "pod spodem" mają miejsce skomplikowane i (ze względu na nasz kulinarny model domenowy ) nieistotne zjawiska. Jak mógłby powyższy przepis wyglądać gdyby był częścią programu tworzonego przez nierozgarniętego programistę?


dodaj(maslo)

while(maslo.nieJestStopione){
  for( atom in atomyWProbceMasla){
   atom.dostarczEnergii
  }
}
dodaj(pokrojona Szynka)

while(szczypiorek.jestCaly){
  oddziaływuj nożem na sieć krystaliczną szczypiorku
}

dodaj(szczypiorek)

noż.dodajEnerigiiPotencjalnej
noz.zamieńEnergięPotencjalnąNaKinetyczną
noż.uderzW(jajko)

dodaj(zawartośćJajka)

dodaj(sól) 

for(ziarnkoPieprzu in szczyptaPipeprzu){
 dodaj(ziarnkoPieprzu)
}

i mieszać, aż do momentu ścięcia się jajek


(poprawność kwestii fizycznych może być niedokładna ale nie to jest meritum przykładu)


Tak zmieniony przepis o wiele trudniej zrozumieć i co gorsza domena kulinarna została zmieszana z domena fizyczną przez co potencjalny odbiorca przepisu musi zmierzyć się ze znacznie większą płaszczyzną problemu.

Aby zachować jeden poziom abstrakcji wracamy do korzeni:


patelnia.dodaj(maslo)
patelnia.podgrzejDoRostopieniaMasla()
patelnia.dodaj(pokroj(szynka))
patelnia.dodaj(pokroj(szczypiorek))
patelnia.dodaj(rozbij(jajko))
patelnia.dodaj(sól)
patelnia.dodaj(pieprz)
mieszajDoMomentuScieciaSieJajek(patelnia)


Poprawione źródło przepisu jest czytelniejsze i nie wymaga znajomości zagadnień wykraczających poza domenę kulinarną. Widzimy także ciekawy efekt wizualny, który może być użyty jako swoisty test czy nie wykraczamy poza dany obszar abstrakcji : mianowicie wersja poprawiona nie ma wcięć.

Jak przedstawione zjawisko mogłoby wyglądać na przykładzie bardziej zbliżonym do IT?


funkcja(obiekt){
operacjaDomenowa();
bebechy=obiekt.wyciągnijBebechy
...
kilka zagnieżdzonych pętli i try-catch
...
operacja domenowa()
znowuGrzebanieWBEbechach()
}


przykład konkretny : obsługujemy request od przeglądarki, który może zawierać obrazki i załączniki tekstowe. Każdy typ załącznika musimy zapisać do osobnego katalogu.


przetworzRequest(request){
   zapiszPlikiTekstowe(request)
   zapiszObrazki(request)
}



A można i tak :


przetworzRequest(request){
 zapiszPlikiTekstowe(request)

 strumien=OtworzStrumien
 for(bit in obrazek){
   strumien.pisz(bit)
 }
 strumien.zamknij
}



Chyba jest jasne,która wersja będzie czytelniejsza,przyjemniejsza,wygodniejsza i łatwiejsza w utrzymaniu osobie, która ujrzy ów fragment po raz pierwszy w życiu.

niedziela, 30 stycznia 2011

Bardzo uproszczone modele naszego umysłu

Poniżej przedstawię praktyczną aplikację pomagającą osiągać stan umysłu gwarantujący lepsze skupienie w trakcie tworzenia kodu jakkolwiek na początku pojawi się niezwykle uproszczony koncepcyjny model ludzkiego umysłu. Ta odrobina teorii pomoże zrozumieć filozofię i ideę działania programu Brain Wave Generator.

Bardzo uproszczony model psychologiczny



Poniższy rysunek psychologicznego modelu umysłu.



W dużym skrócie: odbierane przez zmysły naszej percepcji informacje trafiają do nieświadomej części umysłu - prawdziwie potężnego komputera biologicznego, który to odpowiednio filtruje i zniekształca otrzymane w ten sposób dane, zaś następnie w tak zmienionej formie przekazuje je do części świadomej.


Umysł świadomy zdolny jest do abstrakcyjnego i krytycznego operowania na danych jednakże w jednej chwili jest w stanie zapanować nad małą liczbą niezależnych pojęć (w zależności od badań ten zakres kształtuje się w granicach 4-9). Umysł nieświadomy jest w stanie przetwarzać niesamowite ilości informacji jednakże dane ze otaczającego nas świata odbiera on w sposób bezkrytyczny.


Prosty przykład

Umysł nieświadomy kontroluje wszystkie życiowe funkcje twojego organizmu łącznie z oddychaniem. Jednakże gdy przeczytałeś ostatnie zdanie być może zwróciłeś uwagę na swój proces oddychania. Możesz teraz kontrolować każdy wdech i wydech jednakże zużywając świadomy zasób umysłu będzie ci teraz trudniej koncentrować się na bardziej skomplikowanych czynnościach. Za kilka minut zapomnisz o tym tekście i ponownie oddychanie stanie się domeną umysłu nieświadomego.

Model mechaniczny


Spójrzmy teraz na umysł/mózg od strony "mechanicznej". Chyba dla nikogo nie jest czymś zaskakującym, iż posiadamy dwie półkule mózgowe jakkolwiek nie każdy zdaje sobie sprawę co należy do obowiązków danej półkuli. W dużym (znowu) uproszczeniu lewa półkula zajmuje się analizą zaś prawa posiada duszę artysty. Optymalnym stanem pracy jest synchronizacja pomiędzy obydwiema połówkami mózgu i w tym momencie na scenie pojawia się pojęcie częstotliwości pracy naszych neuronów.


Naszym naturalnym trybem jest tryb czuwania charakteryzujący się częstotliwością kilkunastu- kilkudziesięciu Hz. W tym stanie jesteśmy nastawieni na odbieranie bodźców ze świata zewnętrznego i jest on przydatny raczej w wypadku ucieczki przed lwem aniżeli skupieniem się nad pisaniem kodu. Bardziej wydajny tryb pracy uzyskamy schodząc do częstotliwości 8-12 Hz , czyli tzw. częstotliwości alfa. Gdy neurony pracują ze wspomnianą częstotliwością osiągamy stan kontemplacji i skupienia pomagający w niezwykłym stopniu budować wewnątrz naszej "pamięci operacyjnej" mentalny model tworzonej abstrakcji programistycznej.


Pytanie jak osiągnąć wspomniany stan. Sposobów jest kilka. Jednym jest uspokojenie oddechu i wprowadzenie swojego ciała w stan relaksacji. Możemy również użyć aplikacji wspomnianej na początku artykułu. Program pozwala wybrać częstotliwość dźwięków za która będzie podążał nasz umysł.




Użytkownicy linuxa muszą używać BrainWave generatora poprzez Wine.


Wkrótce kolejne artykuły.