IT rekvalifikace s garancí práce. Seniorní programátoři vydělávají až 160 000 Kč/měsíc a rekvalifikace je prvním krokem. Zjisti, jak na to!
Hledáme nové posily do ITnetwork týmu. Podívej se na volné pozice a přidej se do nejagilnější firmy na trhu - Více informací.

Lekce 23 - Nejčastější chyby Java nováčků - Umíš pojmenovat objekty?

V minulé lekci, OOP v Javě naposledy - Boxing, balíčky a doplnění, jsme se zabývali balíčky a dalšími OOP konstrukcemi.

V dnešním Java tutoriálu si ukážeme první dobré praktiky pro objektově orientované programování v Javě. Podívej se, jestli neděláš jednu z nejčastějších chyb.

Slovo senior programátora

David Čápka - Objektově orientované programování v Javě

Gratuluji ke zdolání základní problematiky objektově orientovaného programování! 🏆 Dostal jsi se k záchytnému bodu, ve kterém se trochu vydýcháme a ukážeme si, jak správně použít nabyté informace, než se pustíme do dalších. Materiál pro dnešní lekci jsem sestavil na základě 20letých zkušeností s programováním a její obsah bude mít zásadní vliv na tvé ohodnocení na trhu práce.

Milionové ztráty

O dobrých praktikách jsme se již bavili v kurzu Základní konstrukce jazyka Java a víme, že nepřehledné programy nejsou vůbec žádná malichernost. Jsou totiž:

  • Nesrozumitelné pro ostatní - Když tým 5 programátorů, každý s platem 100.000 Kč měsíčně, stráví 20 % pracovní doby luštěním kódu, stojí to ročně 1.2 milionu Kč!
  • Náchylné k chybám - Tržby i malých e-shopů jsou měsíčně obvykle v milionech korun, 1 den nefunkčnosti tedy stojí majitele stovky tisíc Kč, dodavateli hrozí nemalé smluvní pokuty.
  • Prakticky nerozšiřitelné - Ve stávající funkčnosti se už nikdo nevyzná a nelze ji rozšířit. Programátorský tým o několika lidech musí vytvořit aplikaci znovu, jsme opět v milionech Kč.
  • Netestovatelné, nezabezpečené a takto bychom mohli pokračovat.

Není pochyb, že dobré praktiky jsou pro vývoj softwaru v týmu naprosto zásadní a následky jejich porušení potom naprosto fatální.

Jak správně pojmenovávat třídy, atributy a metody?

Umíme vytvářet spoustu nových objektových konstrukcí, v programech nám vzniká množství nových identifikátorů (jmen). V dnešní lekci se budeme zabývat tím, jak "objektové součástky" našich aplikací správně pojmenovat, aby byly přehledné.

Motivační příklad

K doktorovi přijde pacient a říká mu, že má problém se svým orgánem Presouvat. Nefunguje mu bota. Pacient se zdá být nějaký popletený a doktorovi trvá poměrně dlouho, než z něj dostane, že ho píchá v patě a proto si nemůže nazout ani botu. Když konečně vypustí pacienta z ordinace, zjistí, že byl součástí skupiny a takových jich tam ještě čeká několik desítek.

Objektově orientované programování v Javě

Podívejme se ještě na druhý příběh. Programátorovi přidělí program, který spadne s chybou ve třídě PresouvatData, metoda data(). Program se zdá být nějaký popletený a programátorovi trvá dlouho, než zjistí, že se jedná o třídu importující data z externí zálohy a že se prvně musí ručně zavolat metoda pracuj(), která import provede. Když chybu konečně opraví, objeví se další a zjistí, že v programu je několik desítek tříd a metod, z jejichž názvu vůbec nepozná, co dělají.

Určitě vidíme paralelu těchto dvou příběhů. Zatímco u lidského těla by nás asi těžko napadlo hovořit o orgánu "přesouvat" a funkci "bota", v programech bohužel není takový problém narazit na objekty pojmenované jako děje a funkce pojmenované jako věci, i když je princip úplně stejný. Není divu, že si Indescriptive naming vysloužilo své místo v šestici nejhorších programátorských praktik STUPID.

Pojmenování tříd

Třídy definují objekty, ze kterých je aplikace složená. Z toho vyplývá několik triviálních pravidel. Názvy tříd:

  • jsou podstatná jména! - Jedná se o jednotlivé počitatelné objekty bez ohledu na to, kolik objektů od třídy potom vytvoříme.
  • nejsou názvy dějů - Jde o objekty (věci). Třídy tedy nemůžeme nazvat např. PraceSeSouborem nebo Vypisovani, ale např. SpravceSouboru nebo Vypisovac (nebo ještě lépe UzivatelskeRozhrani, protože zřídka kdy tvoříme celou třídu jen na vypsání něčeho).
  • začínají s velkým písmenem - Každé další slovo má velké písmeno (notace) PascalCase. Je tak vidět, že jde o obecnou třídu a ne o její konkrétní instanci.
  • jsou pojmenované podle toho, jakou součást programu reprezentují, což nemusí být vždy stejné, jako to, co uvnitř dělají.

Ukažme si několik příkladů:

✗ Špatně

class zamestnanec {
class Zamestnanci {
class Polozkafaktury {
class PraceSeSouborem {
class Vytiskni {
class ZadavaniUdaju {

✔ Správně

class Zamestnanec {
class SpravceZamestnancu {
class PolozkaFaktury {
class SouborovaDatabaze {
class UzivatelskeRozhrani {

Pokud narazíte na program, kde se třída jmenuje PraceSeSouborem, jeho autor si pravděpodobně jen vygooglil, že kód se píše do class, aniž by tušil, že tím založil nějaký objekt.

Třídy v množném čísle

V množném čísle pojmenováváme třídy velmi zřídka. V Javě takto nalezneme např. třídu Arrays. Od té nevytváříme instance a používáme ji jen pro práci s instancemi třídy Array, tedy s poli. Pole setřídíme např. jako:

Arrays.sort(zamestnanci);

Osobně by mi mnohem větší smysl dávalo, aby tyto metody měla na sobě přímo třída Array a psali jsme tedy:

zamestnanci.sort()

Autoři Javy pravděpodobně nechtěli třídu Array příliš složitou a tak pro některé metody vytvořili tuto druhou třídu. Výsledný přínos je diskutabilní. My třídy v množném čísle většinou deklarovat nebudeme.

Pojmenování tříd v angličtině

Základní kurzy jsou na ITnetwork česky, aby byly lépe stravitelné. Kódy těch pokročilých jsou stejně jako reálné obchodní aplikace anglicky. Pro anglické názvy tříd platí samozřejmě to samé, co jsme řekli výše. Můžeme ovšem snadno udělat následující chyby:

  • Jednotná čísla - Když v češtině pojmenujeme třídu pracující s auty SpravceAut, mohl by se nabízet anglický překlad CarsManager. Správně je ovšem CarManager, jednotné číslo, protože Car zde funguje jako přídavné jméno.
  • Pořadí slov - Na rozdíl od češtiny je podstatné jméno na konci sousloví, správce aut tedy není ManagerCars nebo ManageCars, ale CarManager. Cesta k souboru není PathFile (což by byl cestový soubor), ale FilePath apod.

V angličtině se u tříd často používá koncovka -er, např. TaskRunner, podle toho, co třída dělá.

Ukažme si pár příkladů:

✗ Špatně

class CarsManager {
class PathFile {
class RunTasks {

✔ Správně

class CarManager {
class FilePath {
class TaskRunner {

Pojmenování atributů

Atributy jsou "proměnné" dané třídy. Pro jejich pojmenování tedy platí úplně ty samé zásady jako pro proměnné, které si již detailně vysvětlovali v lekci Nejčastější chyby Java nováčků - Umíš pojmenovat proměnné?.

Základním pravidlem opět je, že atributy pojmenováváme podle toho, co je v nich uloženo. Název atributu chápeme v kontextu názvu třídy a nemusí tedy dávat smysl sám o sobě. Z jazykového hlediska jsou názvy atributů:

  • podstatná jména (jmeno, zamestnanci, ...)
  • přídavná jména (vypnuty, odeslano, ...)

Připomeňme si zde i zbylé zásady:

  • všechny atributy pojmenováváme buď česky bez diakritiky nebo anglicky, ale ne kombinací těchto jazyků
  • víceslovné atributy pojmenováváme pomocí notace camelCase
  • pokud atribut obsahuje kolekci s více hodnotami (např. pole nebo List), je jeho název v množném čísle

Ukažme si opět nějaké příklady názvů atributů tříd:

✗ Špatně

private String Jmeno;
private boolean odeslat;
private String[] telefonnicislo;
private JButton tlačítko;
private Address[] uzivatelAddress;

✔ Správně

private String jmeno;
private boolean odeslano;
private String[] telefonniCisla;
private JButton tlacitko;
private Address[] adresyUzivatele;

Pojmenování metod a parametrů

Metody označují děje, jejich název obsahuje tedy sloveso! Může se jednat o:

  • přikazovací tvar (nacti(), nastavId()) - Metoda převážně provádí nějakou činnost a její výsledek může nebo nemusí vracet. Nevolíme infinitiv, např. nacitat().
  • tázací tvar - Metodou se převážně ptáme na nějakou hodnotu, než abychom chtěli provést nějakou akci (česky např. vratJmeno() nebo jeVypnuty() pro proměnné typu boolean, anglicky např. getRank(). Již víme, že takovým metodám říkáme gettery.

Metody pojmenováváme podle toho, co dělají! Vyhýbáme se neurčitým názvům jako pracuj(), akce(), run() apod.

Ukažme si příklady:

✗ Špatně

public void vypisovani(Zakaznik zakaznik) {
public boolean vratZapnuty() {
private void data() {
public void pracuj() {

✔ Správně

public void vypis(Zakaznik zakaznik) {
public boolean jeZapnuty() {
private void vygenerujData() {
public void importujZalohu() {

Parametry metod

Parametr metody je proměnná a proto pro jejich název platí ta samá pravidla, jako pro proměnné a atributy (například nikdy nepojmenujeme parametr param :) ). Je tu ovšem jedna důležitá věc na uvážení a to je použití dvojí negace. Ukažme si poslední příklad:

✗ Špatně

public void importujData(boolean zakazatCiziKlice) {

importujData(false);

✔ Správně

public void importujData(boolean povolitCiziKlice) {

importujData(false);

Kdo z vás na první dobrou dokáže říci, jestli jsou v první variantě s předáním hodnoty false klíče povoleny? Vše je zas o lidském mozku, který není zvyklý fungovat pod dvojí negací. Volíme tedy spíše druhou variantu.

V příští lekci, Jak správně rozdělit Java aplikace do tříd - SRP a SoC, si vysvětlíme dobré praktiky SRP (Single Responsibility Principle) a SoC (Separation of Concerns). Nakousneme také téma závislostí.


 

Předchozí článek
OOP v Javě naposledy - Boxing, balíčky a doplnění
Všechny články v sekci
Objektově orientované programování v Javě
Přeskočit článek
(nedoporučujeme)
Jak správně rozdělit Java aplikace do tříd - SRP a SoC
Článek pro vás napsal David Hartinger
Avatar
Uživatelské hodnocení:
313 hlasů
David je zakladatelem ITnetwork a programování se profesionálně věnuje 15 let. Má rád Nirvanu, nemovitosti a svobodu podnikání.
Unicorn university David se informační technologie naučil na Unicorn University - prestižní soukromé vysoké škole IT a ekonomie.
Aktivity