OOP jazyk - problém klasického stříhu

Youda

Re:OOP jazyk - problém klasického stříhu
« Odpověď #60 kdy: 08. 06. 2018, 08:18:59 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

S tímhle souhlasím, otázka tedy teď je, co je špatného na User.save()?

Hlavni myslenkou za OOP a proc se stal nejpouzivanejsim paradigmatem je pristup, ze defacto reflektuje/modeluje svet kolem nas, ktery se sklada z objektu, co vzajemne interaguji. Pak je program snadno uchopitelny a pochpotelny.

Aby ti to bylo jasnejsi, prejmenuj si User na KartotecniListekUsera (protoze presne o toto v danem okamziku jde) a vysledek bude
Knihovnik.zaloz(KartotecniListekUsera)
Kartotecni lustky, co samy skacou do kartoteky jsou v nasem vesmiru mene obvykle.
A naopak, az budes psat simulacni sw simulujici chovani lidi-Useru, pojmenuj si tridu PersonRoleUser a pak je logicky namiste volani PersonRoleUser.skocDoZdi()

Zpet k Userovi, v realu mam nejaky JSF backing bean, ktery ma metodu userChangeSubmitBttnClicked(), to je iniciator. V pripade vyse popsaneho spatneho navrhu, pak musi iniciator invokovat User, aby neco proved. Nenni jediny duvod proc. Navic to vede k prasecinam typu, ze kdyz mi iniciator pteda jenom cast parametru, treba userId a heslo pri changepass, musim vyrobit nekonzistentni poloprazdny objetkt User a na nem zavolat changePass() Nebo zbytecne vytahovat z DB kompletni instanci User, abych ty data k nicemu nepouzil.


Hu

Re:OOP jazyk - problém klasického stříhu
« Odpověď #61 kdy: 08. 06. 2018, 08:25:44 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

S tímhle souhlasím, otázka tedy teď je, co je špatného na User.save()?

Hlavni myslenkou za OOP a proc se stal nejpouzivanejsim paradigmatem je pristup, ze defacto reflektuje/modeluje svet kolem nas, ktery se sklada z objektu, co vzajemne interaguji. Pak je program snadno uchopitelny a pochpotelny.

Aby ti to bylo jasnejsi, prejmenuj si User na KartotecniListekUsera (protoze presne o toto v danem okamziku jde) a vysledek bude
Knihovnik.zaloz(KartotecniListekUsera)
Kartotecni lustky, co samy skacou do kartoteky jsou v nasem vesmiru mene obvykle.
A naopak, az budes psat simulacni sw simulujici chovani lidi-Useru, pojmenuj si tridu PersonRoleUser a pak je logicky namiste volani PersonRoleUser.skocDoZdi()

Zpet k Userovi, v realu mam nejaky JSF backing bean, ktery ma metodu userChangeSubmitBttnClicked(), to je iniciator. V pripade vyse popsaneho spatneho navrhu, pak musi iniciator invokovat User, aby neco proved. Nenni jediny duvod proc. Navic to vede k prasecinam typu, ze kdyz mi iniciator pteda jenom cast parametru, treba userId a heslo pri changepass, musim vyrobit nekonzistentni poloprazdny objetkt User a na nem zavolat changePass() Nebo zbytecne vytahovat z DB kompletni instanci User, abych ty data k nicemu nepouzil.

Bttn. Ty seš čurák.

harrison314

Re:OOP jazyk - problém klasického stříhu
« Odpověď #62 kdy: 08. 06. 2018, 08:36:06 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

S tímhle souhlasím, otázka tedy teď je, co je špatného na User.save()?

No predsa User.Load().
ma to byt na userovi staticky? Alebo konstruktorom vytvoris Usera, ktory sa neda pouzit? Ci ma byt metoda Load niekde inde ako Save?

IMHO som rad ze som Active Record uz davno opustil.

...

Re:OOP jazyk - problém klasického stříhu
« Odpověď #63 kdy: 08. 06. 2018, 09:21:42 »
Ono můžete mít třeba taky tohle a bude to dávat smysl:

Kód: [Vybrat]
@Data
class Vector {
  private double length;
  private float angle;

  public Vector(double length, float angle) {}
}

class Polygon {
  protected List<Vector> vectors;

  protected Polygon() {}

  double calculateVolume() {}
}

class Rectangle extends Polygon {

  Rectangle(double a, double b) {
    vectors.add( new Vector(a, 90.0f) );
    vectors.add( new Vector(b, 90.0f) );
    vectors.add( new Vector(a, 90.0f) );
    // vectors.add( new Vector(b, 90.0f) ); Polygon je vzdy uzavreny.
  }

  double getA() {
    vectors.get(0).getLength();
  }

  double getB() {
    vectors.get(1).getLength();
  }
}

Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.

Konkrétně třeba ten Polygon - ono je to správně OOP, zobecnil jsem celou řadu geometrických tvarů do jednoho jediného, Polygon, a genericky proto můžu počítat obsah, obvod, a další blbiny. V PRAXI ale je lepší se na to vysrat a udělat Rectangle prostě zvlášť, protože takto je to zbytečně překomplikované a postrádá to pointu.

Když budu mít jenom Rectangle, můžu udělat:

Kód: [Vybrat]

@Data
class Rectangle {
  double a;
  double b;

  public double calculateVolume() {
    return a*b;
  }
}

A je to mnohem lepší, ve všech směrech. A teď je tam ta metoda calculateVolume(), zase jde o to, že u takové jednoduché věci typu Rectangle tu metodu můžu mít přímo uvnitř a byl bych asi blbec, kdybych dělal GeometricPatterns.calculateVolume(rectangle);, protože mám takovou pidi třídu, která řeší a obsahuje prd, je izolovaná od okolí, tak přece tam tomu tu metodu dám. Opět, je to ukázkové OOP. Jenže v PRAXI dpč, když budu chtít tohle dělat u trochu kompikovanějších tříd a vztahů, zabřednu opět do sraček. A ze všeho nejhorší na tom OOP je, že nad tím vším musí člověk přemýšlet a filozofovat, když přitom už to mohl mít dávno napsané.

Kit

Re:OOP jazyk - problém klasického stříhu
« Odpověď #64 kdy: 08. 06. 2018, 09:30:20 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

Jak metoda save() zjistí, co z objektu User má uložit? Jak se bez getterů dostane k jeho privátním atributům?

Co se ma ulozit zalisti prislusna metoda repisitory, data zjisti pres gettery. Na gettery je v eclipse dokonce generator

Jaké gettery? To bych musel tyto boilerplates napsat nebo nechat vygenerovat a porušil bych tím zapouzdření.


...

Re:OOP jazyk - problém klasického stříhu
« Odpověď #65 kdy: 08. 06. 2018, 09:46:43 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

Jak metoda save() zjistí, co z objektu User má uložit? Jak se bez getterů dostane k jeho privátním atributům?

Co se ma ulozit zalisti prislusna metoda repisitory, data zjisti pres gettery. Na gettery je v eclipse dokonce generator

Jaké gettery? To bych musel tyto boilerplates napsat nebo nechat vygenerovat a porušil bych tím zapouzdření.

Dělá se to ve Springu tak, pokud teda nepoužiješ Hibernate, že máš prostě Repository::insertUsers(List<User> users); a tam rozepíšeš SQL dotaz, z usera si to vytáhneš ručně přes gettery. Standardně se místo Hibernate používá MyBatis, který umí v XMLku přímo při skládání SQL iterovat nad kolekcemi atd. , takže určit nebudeš ručně tvořit nějaký String :D

No a pokud použiješ Hibernate, tak ten toho User zpracuje reflexí.

A gettery a settery nad POJO třídou určitě nejsou porušení zapouzdření, to už bys mohl vědět, máš na to roky.

Youda

Re:OOP jazyk - problém klasického stříhu
« Odpověď #66 kdy: 08. 06. 2018, 09:48:56 »
Ono můžete mít třeba taky tohle a bude to dávat smysl:

Kód: [Vybrat]
@Data
class Vector {
  private double length;
  private float angle;

  public Vector(double length, float angle) {}
}

class Polygon {
  protected List<Vector> vectors;

  protected Polygon() {}

  double calculateVolume() {}
}

class Rectangle extends Polygon {

  Rectangle(double a, double b) {
    vectors.add( new Vector(a, 90.0f) );
    vectors.add( new Vector(b, 90.0f) );
    vectors.add( new Vector(a, 90.0f) );
    // vectors.add( new Vector(b, 90.0f) ); Polygon je vzdy uzavreny.
  }

  double getA() {
    vectors.get(0).getLength();
  }

  double getB() {
    vectors.get(1).getLength();
  }
}

Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.

Konkrétně třeba ten Polygon - ono je to správně OOP, zobecnil jsem celou řadu geometrických tvarů do jednoho jediného, Polygon, a genericky proto můžu počítat obsah, obvod, a další blbiny. V PRAXI ale je lepší se na to vysrat a udělat Rectangle prostě zvlášť, protože takto je to zbytečně překomplikované a postrádá to pointu.

Když budu mít jenom Rectangle, můžu udělat:

Kód: [Vybrat]

@Data
class Rectangle {
  double a;
  double b;

  public double calculateVolume() {
    return a*b;
  }
}

A je to mnohem lepší, ve všech směrech. A teď je tam ta metoda calculateVolume(), zase jde o to, že u takové jednoduché věci typu Rectangle tu metodu můžu mít přímo uvnitř a byl bych asi blbec, kdybych dělal GeometricPatterns.calculateVolume(rectangle);, protože mám takovou pidi třídu, která řeší a obsahuje prd, je izolovaná od okolí, tak přece tam tomu tu metodu dám. Opět, je to ukázkové OOP. Jenže v PRAXI dpč, když budu chtít tohle dělat u trochu kompikovanějších tříd a vztahů, zabřednu opět do sraček. A ze všeho nejhorší na tom OOP je, že nad tím vším musí člověk přemýšlet a filozofovat, když přitom už to mohl mít dávno napsané.

Ten tvuj "ukazkovy pripad" je ukazkovy pripad spatneho OOP.

Vyse uvedeny priklad je typicky priklad na interface, to znamena za to tvoje class Rectangle si pridej implements Polygon a nad metodu calculateVolume() si pridej anotaci @Overrride. Interface Polygon definuje abstraktni metodu calculateVolume(). S objektem Rectangle budes pracovat a do collections ukladat via interface Polygon.
metoda calculateVolume() samozrejme patri primo do Rectangle, anzto nepracuje s zadnymi daty mimo objekt, coz se pozna snadno, metoda nema zadne parametry.

Inheritance ma smysl v pripade, ze mam nejakou funkcionalitu pripadne si uchovavam nejaky stav na urovni predka a potrebuju rozsirit funkcionalitu predka za vyuziti jeho protected metod a atributu, ke keterym jinak nemam pristup.
Nejcasteji se inheritance pouziva u knihovnich trid, kdy zdedenim modifikuju cast funkcionality a zbytek funkcionality zustava stejny.
Osobne pouzivam inheritanci velice zridka, interfacy prakticky vzdy (pro mockovani)

U vyse uvedeneho prikladu by class Polygon mohl implementovat napr funkcionalitu spolecnou pro vsechny polygony, napada me treba ulozeni casu vzniku prislusneho polygonu a getter na tuto hodnotu.

Znalost OOP znamena i vedet, kdy prislusne konstrukty pouzit.

Youda

Re:OOP jazyk - problém klasického stříhu
« Odpověď #67 kdy: 08. 06. 2018, 09:53:28 »
V pripade Usera je spravny pristup
UserRegistr.save(User)

Jak metoda save() zjistí, co z objektu User má uložit? Jak se bez getterů dostane k jeho privátním atributům?

Co se ma ulozit zalisti prislusna metoda repisitory, data zjisti pres gettery. Na gettery je v eclipse dokonce generator

Jaké gettery? To bych musel tyto boilerplates napsat nebo nechat vygenerovat a porušil bych tím zapouzdření.

Gettery neporusuji zapouzdreni, gettery nemohou modifikovat stav objetku.
Boilerplate getteru neni potreba psat, IDE na to ma generator - tento pristup pouzivam.
Pokud ma nekdo s gettery na spodku classy neprekonatelne potize, necht si to mavenu prida dependency na Lombok.

...

Re:OOP jazyk - problém klasického stříhu
« Odpověď #68 kdy: 08. 06. 2018, 09:54:01 »
Ono můžete mít třeba taky tohle a bude to dávat smysl:

Kód: [Vybrat]
@Data
class Vector {
  private double length;
  private float angle;

  public Vector(double length, float angle) {}
}

class Polygon {
  protected List<Vector> vectors;

  protected Polygon() {}

  double calculateVolume() {}
}

class Rectangle extends Polygon {

  Rectangle(double a, double b) {
    vectors.add( new Vector(a, 90.0f) );
    vectors.add( new Vector(b, 90.0f) );
    vectors.add( new Vector(a, 90.0f) );
    // vectors.add( new Vector(b, 90.0f) ); Polygon je vzdy uzavreny.
  }

  double getA() {
    vectors.get(0).getLength();
  }

  double getB() {
    vectors.get(1).getLength();
  }
}

Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.

Konkrétně třeba ten Polygon - ono je to správně OOP, zobecnil jsem celou řadu geometrických tvarů do jednoho jediného, Polygon, a genericky proto můžu počítat obsah, obvod, a další blbiny. V PRAXI ale je lepší se na to vysrat a udělat Rectangle prostě zvlášť, protože takto je to zbytečně překomplikované a postrádá to pointu.

Když budu mít jenom Rectangle, můžu udělat:

Kód: [Vybrat]

@Data
class Rectangle {
  double a;
  double b;

  public double calculateVolume() {
    return a*b;
  }
}

A je to mnohem lepší, ve všech směrech. A teď je tam ta metoda calculateVolume(), zase jde o to, že u takové jednoduché věci typu Rectangle tu metodu můžu mít přímo uvnitř a byl bych asi blbec, kdybych dělal GeometricPatterns.calculateVolume(rectangle);, protože mám takovou pidi třídu, která řeší a obsahuje prd, je izolovaná od okolí, tak přece tam tomu tu metodu dám. Opět, je to ukázkové OOP. Jenže v PRAXI dpč, když budu chtít tohle dělat u trochu kompikovanějších tříd a vztahů, zabřednu opět do sraček. A ze všeho nejhorší na tom OOP je, že nad tím vším musí člověk přemýšlet a filozofovat, když přitom už to mohl mít dávno napsané.

Ten tvuj "ukazkovy pripad" je ukazkovy pripad spatneho OOP.

Vyse uvedeny priklad je typicky priklad na interface, to znamena za to tvoje class Rectangle si pridej implements Polygon a nad metodu calculateVolume() si pridej anotaci @Overrride. Interface Polygon definuje abstraktni metodu calculateVolume(). S objektem Rectangle budes pracovat a do collections ukladat via interface Polygon.
metoda calculateVolume() samozrejme patri primo do Rectangle, anzto nepracuje s zadnymi daty mimo objekt, coz se pozna snadno, metoda nema zadne parametry.

Inheritance ma smysl v pripade, ze mam nejakou funkcionalitu pripadne si uchovavam nejaky stav na urovni predka a potrebuju rozsirit funkcionalitu predka za vyuziti jeho protected metod a atributu, ke keterym jinak nemam pristup.
Nejcasteji se inheritance pouziva u knihovnich trid, kdy zdedenim modifikuju cast funkcionality a zbytek funkcionality zustava stejny.
Osobne pouzivam inheritanci velice zridka, interfacy prakticky vzdy (pro mockovani)

U vyse uvedeneho prikladu by class Polygon mohl implementovat napr funkcionalitu spolecnou pro vsechny polygony, napada me treba ulozeni casu vzniku prislusneho polygonu a getter na tuto hodnotu.

Znalost OOP znamena i vedet, kdy prislusne konstrukty pouzit.

Nechápu proč používáš Interfacy ve Springu kvůli Mockování, mockovat můžeš klidně i třídu, přes reflexi. Potom je z těch Interface akorát bordel, přes který se musíš pořád proklikávat a kničemu to neslouží. To se dělalo ve staré verzi Springu, který si neuměl vytvořit reflexí proxy beanu.

JSH

Re:OOP jazyk - problém klasického stříhu
« Odpověď #69 kdy: 08. 06. 2018, 09:55:29 »
Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.
Hlavní problém je IMO to, že OOP objekty nejsou vůbec "objekty" jak ten pojem používáme v reálném světě.

OOP objekt mívá stav, který se v čase obvykle mění a má nějakou funkčnost, takže umí sám něco dělat. V původním OOP to jde ještě do většího extrému, kdy posláním zprávy ten objekt o něco žádám. Ten stav by se dal zahodit, ale to že žádám _jeden_ objekt o něco je problém.

- Matematické objekty nejsou OOP objekty. Žádný matematický objekt neumí nic sám spočítat. Navíc ve většině výpočtů figuruje víc rovnocenných matematických objektů, takže ani není jasné kterému ten výpočet vůbec dát.
- Většina reálných objektů nejsou OOP objekty, protože samy od sebe vůbec nic neumí. V realitě existuje jen pár plnotučných OOP objektů (které bych spíš nazval actory) a zbytek jsou tupá "data".

Youda

Re:OOP jazyk - problém klasického stříhu
« Odpověď #70 kdy: 08. 06. 2018, 10:02:42 »

Nechápu proč používáš Interfacy ve Springu kvůli Mockování, mockovat můžeš klidně i třídu, přes reflexi. Potom je z těch Interface akorát bordel, přes který se musíš pořád proklikávat a kničemu to neslouží. To se dělalo ve staré verzi Springu, který si neuměl vytvořit reflexí proxy beanu.

To je pravda. Mockoval jsem naposled ve starem springu. ted uz jsem mocky dlouho k nicemu nepotreboval.

Youda

Re:OOP jazyk - problém klasického stříhu
« Odpověď #71 kdy: 08. 06. 2018, 10:09:39 »
Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.
Hlavní problém je IMO to, že OOP objekty nejsou vůbec "objekty" jak ten pojem používáme v reálném světě.

OOP objekt mívá stav, který se v čase obvykle mění a má nějakou funkčnost, takže umí sám něco dělat. V původním OOP to jde ještě do většího extrému, kdy posláním zprávy ten objekt o něco žádám. Ten stav by se dal zahodit, ale to že žádám _jeden_ objekt o něco je problém.

- Matematické objekty nejsou OOP objekty. Žádný matematický objekt neumí nic sám spočítat. Navíc ve většině výpočtů figuruje víc rovnocenných matematických objektů, takže ani není jasné kterému ten výpočet vůbec dát.
- Většina reálných objektů nejsou OOP objekty, protože samy od sebe vůbec nic neumí. V realitě existuje jen pár plnotučných OOP objektů (které bych spíš nazval actory) a zbytek jsou tupá "data".

Mno objekty jsou oba, ten vas "actor" i ty "tupa data" - a i ty zamozrejme "neco umi" - umi encapsulovane drzet data a pripadne generovat pohledy na jejich interni data.
"actoru" se v terminologii springu rika @Component, ktery se podle pouziti deli na @Controller, @Service a @Repository. Mezi nimi pobihaji proste POJOs, pripadne ORM entity, pripadne jejich kolekce.

Kiwi

Re:OOP jazyk - problém klasického stříhu
« Odpověď #72 kdy: 08. 06. 2018, 10:46:16 »
Jenže v PRAXI dpč, když budu chtít tohle dělat u trochu kompikovanějších tříd a vztahů, zabřednu opět do sraček. A ze všeho nejhorší na tom OOP je, že nad tím vším musí člověk přemýšlet a filozofovat, když přitom už to mohl mít dávno napsané.
Ještě větší problém je, když pak člověku takový projekt přistane na stůl s požadavkem změnit X a Y a dodělat Z. To pak opravdu bez přehánění většinu času stráví přemýšlením, jak to do toho zakomponovat, aby toho nemusel rozbíjet nebo předělávat příliš mnoho, ačkoli pokud jde o rozsah toho kódu, co má něco dělat, je to často jen pár řádků.

Tohle se prostě zvrhlo. Používají se jazyky, které o sobě tvrdí, že jsou objektové, ale ve skutečnosti nejsou, jsou strašně komplikované, nepřehledné, kód v nich je nepřehledný, obsahuje spoustu balastu, v němž se ta funkcionalita ztrácí a rozmělňuje. Lidi tu šermují s výrazy, že ani nevím, jestli mluvěj tak špatně anglicky nebo česky, pořádně se ani neshodnou na tom, co to znamená, ale nedá se říct, že by dnes vznikaly programy kvalitnější než před 30 lety. Fakt si říkám, že lidi by měli přestat vymýšlet p.čoviny a místo toho se konečně naučit programovat. Průměrný programátor z doby před 30 lety kdyby viděl tuhle diskusi, tak by většině věcí vůbec nerozuměl, ale věřím, že by konkrétní problém dokázal vyřešit rychleji a elegantněji i bez všech těch nesmyslů.

JSH

Re:OOP jazyk - problém klasického stříhu
« Odpověď #73 kdy: 08. 06. 2018, 10:53:33 »
Jenže problém je v tom, že tohle OOP vypadá OK na takové kravince jako jsou geometrické útvary, ale v PRAXI, když se snažím reálnou úlohu udělat takto OOP, zabřednu do sraček a je lepší se na to úplně vykašlat. Podle mě má to OOP hoodně omezené použití na velmi malou množinu úloh.
Hlavní problém je IMO to, že OOP objekty nejsou vůbec "objekty" jak ten pojem používáme v reálném světě.

OOP objekt mívá stav, který se v čase obvykle mění a má nějakou funkčnost, takže umí sám něco dělat. V původním OOP to jde ještě do většího extrému, kdy posláním zprávy ten objekt o něco žádám. Ten stav by se dal zahodit, ale to že žádám _jeden_ objekt o něco je problém.

- Matematické objekty nejsou OOP objekty. Žádný matematický objekt neumí nic sám spočítat. Navíc ve většině výpočtů figuruje víc rovnocenných matematických objektů, takže ani není jasné kterému ten výpočet vůbec dát.
- Většina reálných objektů nejsou OOP objekty, protože samy od sebe vůbec nic neumí. V realitě existuje jen pár plnotučných OOP objektů (které bych spíš nazval actory) a zbytek jsou tupá "data".

Mno objekty jsou oba, ten vas "actor" i ty "tupa data" - a i ty zamozrejme "neco umi" - umi encapsulovane drzet data a pripadne generovat pohledy na jejich interni data.
"actoru" se v terminologii springu rika @Component, ktery se podle pouziti deli na @Controller, @Service a @Repository. Mezi nimi pobihaji proste POJOs, pripadne ORM entity, pripadne jejich kolekce.
Já ale psal o vztahu reálných a OOP objektů. Hlavně v kontextu předchozích příspěvků, které se snažily napasovávat OOP objekty 1:1 na reálné objekty.

Gődel

Re:OOP jazyk - problém klasického stříhu
« Odpověď #74 kdy: 08. 06. 2018, 11:02:10 »
Fakt si říkám, že lidi by měli přestat vymýšlet p.čoviny a místo toho se konečně naučit programovat. Průměrný programátor z doby před 30 lety kdyby viděl tuhle diskusi, tak by většině věcí vůbec nerozuměl, ale věřím, že by konkrétní problém dokázal vyřešit rychleji a elegantněji i bez všech těch nesmyslů.
Záleží na definici programátora. Dnes píše kód kdeco, co má do pr..le díru, a podle toho pak kód vypadá. Takový zubař samouk to má těžší, u něj se přijde rychle na to, že nemá diplom - Jahelka by mohl vyprávět. Podle zkušeností nejlepší kód píšou inteligentní a vzdělaní lidé, ovšem z jiných oborů (fyzika, biologie, chemie, geologie...), protože se s tím nepářou a moc nešpekulujou, prostě sednou a napíšou funkční aplikaci, aniž by přemýšleli, jestli kružnice dědí z obdélníku nebo naopak, ani neřeší, kolik andělů může tančit na špičce monády.