Felhasználói eszközök

Eszközök a webhelyen


oktatas:programozas:tisztakod

Ez a dokumentum egy előző változata!


< Programozás

Tisztakód

A tisztakód

A programozók sokkal több kódot olvasnak mint írnak, ezért fontos, hogy kód ne legyen zavaros, mint a mocsár. A haladó programozók tudják, hogy a zavaros kódok, amiket vissza kell olvasni, nagyban lassítják a munkát. Mégis, sokszor úgy érzik, nekik is ilyet kell írniuk, csakhogy haladjon a munka. Az ilyen kód lehúz mint a mocsár, és nem fogjuk tudni tartani a határidőt.

A kódot ezért úgy kell megírni, hogy mindig olvasmányos legyen, kevés ránézéssel tudjuk mit csinál, meglepetések nélkül.

A kód tisztán írása és tartása, művészet.

Ez a rövid leírás Robert Martin: Tiszta kód című könyve alapján készül.

Elnevezések

Beszédes nevek

A változók, állandók, osztályok és függvények létrehozása során a rossz névadás a kódmocsár irányába lökjük a kódunkat.

A jó elnevezéshez három dolgot vizsgáljunk meg az elnevezendő részről:

  • mi az oka létezésének
  • mit csinál, mi a szerepe
  • hogyan használjuk

Ha úgy érezzük megjegyzést kell fűzni egy változóhoz vagy állandóhoz, biztosan rossz az elnevezése.

int a; //A háromszög alapja

Félrevezetés

Kerüljük a félrevezető elnevezéseket. A közismert nevek például félrevezetők.

A bin, például Unix alapú rendszerekben a bináris szóra utal, illetve kettes számrendszerben megadott számokra is utalhat. Ha mi a belső indexet így szeretnénk rövidíteni, az félrevezető.

Példák az ismert azonosítókra, közismert és egyéni értelemmel:

  • bin - binary
    • belső index
  • pc - personal computer
    • pozitív cél
  • tv
    • tiltott viselkedés
    • tevékenység

A List szó félrevezető, ha olyan gyűjtemény nevében használjuk, ami nem List szerkezetben van tárolva. Például:

dolgozoList

Ilyenkor válasszuk például a következőket:

dolgozoCsoport
dolgozok

Az O használata is megtévesztő lehet:

if( 0 == 35)

A nevek kimondhatósága

Válasszunk olyan neveket, amit könnyű kimondani. Ha egy névben nincsenek magánhangzók, nem könnyű azokat kimondani.

A dkn, a dolgozó keresztnevének rövidítésre például nem ajánlott:

dkn - dolgozó keresztnevek

Legyen helyette:

dolgozoKeresztnev

A nevek kereshetősége

Az egybetűs azonosítók keresése rémálom. Kerüljük a használatát.

Típuskódolás

A névben a típus kódolása kerülendő. Régebben indokoltak voltak ezek az eljárások, mint a „magyar jelölés”, vagy az tagváltozó jelölése. A tagváltozót egy m_ karakter előtag párral jelölhetjük.

A felületek (interfész) nevébe sem ajánlott beletenni a i vagy I karaktereket. Helyette tegyük a hozzátartozó megvalósításba mondjuk Imp szót, vagy magyarul Megval, vagy hasonló szót.

DolgozoGyarMegvalositas
DolgozoGyarMeg

Osztálynevek

Az osztálynevek legyenek mindig főnevek vagy főnévi kifejezések.

Robert Martin szerint kerülendők még a következő szavak az osztályok neveiben: Manager, Processor, Data, Info és hasonlók.

Tagfüggvények

A tagfüggvények nevei mindig igék, vagy igei kifejezések.

Az elérő függvények előtagjai legyenek:

  • set
  • get
  • is

Ha magyar tagfüggvény neveket használunk, akkor nem valami szép az ilyen név:

getNev()

Ez hunglish nyelven van írva, azaz félig magyar, félig angol. Ha mégis mellette döntünk, akkor használjuk következetesen. Jobb ötlet megkeresni a szavak angol megfelelőjét:

getName()

Esetleg a get, set és is helyett magyar változatok keresése:

lekerNev()
beallitNev()

Az is helyett nehéz a magyar nyelvben megfelelő szót találni.

A konstruktorok túlterhelése helyett, használjunk gyártó metódust.

Dolgozo dolgozo = Dolgozo.nevvel("Nagy János");

Jófejkedés

Kerüljük a jófejkedést, például szülőfüggvényecske.

Egy fogalom, ugyanaz a szó

Ha egy fogalomra használunk egy szót, akkor legyünk következetesek és mindig ezt használjuk.

fetchName()
fetchCity()
fetchSalary()

Vagy:

getName()
getCity()
getSalary()

Szóviccek

A szóvicceket is kerüljük, de mit értünk szóvicc alatt? Két eltérő fogalmat ugyanazzal a szóval jelölünk.

Megoldás és feladat tartományok

Ha van megoldástartományból a szakmában használatos név, használjuk azt. Ha nincs maradhat a feladattartomány.

Gyakorlat 01

Feladat 01

Vajon mit csinál a következő függvény?

trinangleCalc();

Többet mond, ha paraméterrel kell hívni?

triangleCalc(30, 35, 45);

Feladat 02

Adott egy metódus, amely beállítja egy jármű sebességét, véletlenszerűen. Vagy gyorsít vagy lassít.

public Car extends JComponent {
    int d;
    Integer e;
    Car() {
 
    }   
    public void doit(){
        Random a = new Random();
        boolean b = a.nextBoolean();
        int c = a.nextInt(3) + 1;       
 
        if(b) {
            if(d>(this.e + c)) {
                this.e = this.e + c;
            }
        }else {
            if((this.e - c) >0){
                this.e = this.e - c;
            }
        }       
    }
 
}

Függvények

Méret

A függvények mérete legyen minél kisebb. Ha 3-4 sor, akkor az már jó. Ennek eredménye lehet, hogy egy if vagy while törzsében csak egy függvényhívás van. Ez jó. Ha ilyen rövid függvényeink vannak, akkor valószínűleg elkerültük az egymásba ágyazott kifejezéseket is.

Egyetlen feladat

Egy függvény csak egyetlen feladatot csináljon, de azt jól csinálja.

Sorrend

A függvényeket fentről lefele írjuk egymás után. Ezt nevezik leszállószabálynak.

Triangle.java
package haromszog;
 
public class Haromszog {
 
    public static void main(String[] args) {
 
        double perimeter = calcPerimeter(30, 35, 40);
        System.out.println("Perimeter: " + perimeter);
    }
 
    public static double calcPerimeter(double sideA, double sideB, double sideC) {        
        double perimeter = -1;
        if(isEditable(sideA, sideB, sideC)) {
            perimeter = sideA + sideB + sideC;
        }
        return perimeter;
    }
 
    public static boolean isEditable(double sideA, double sideB, double sideC) {
        boolean editable = true;
        if(sideA + sideB < sideC) {
            editable = false;
        }
        if(sideA + sideC < sideB) {
            editable = false;
        }
        if(sideB + sideC < sideA) {
            editable = false;
        }
        return editable;
    }
}

Javított verzió

Sides.java
class Sides {
    double a, b, c;
    public Sides(double a, double b, double c) {
        this.a = a;
        this.b = b;
        this.c = c;
    }
}
Triangle.java
public class Triangle {
 
    public static void main(String[] args) {
        Sides sides = new Sides(30, 35, 40);
        double perimeter = calcPerimeter(sides);
        System.out.println("Perimeter: " + perimeter);
    }
 
    public static double calcPerimeter(Sides sides) {        
        double perimeter = -1;
        if(isEditable(sides)) {
            perimeter = sides.a + sides.b + sides.c;
        }
        return perimeter;
    }
 
    public static boolean isEditable(Sides sides) {
        boolean editable = true;
        if(sides.a + sides.b < sides.c) {
            editable = false;
        }
        if(sides.a + sides.c < sides.b) {
            editable = false;
        }
        if(sides.b + sides.c < sides.a) {
            editable = false;
        }
        return editable;
    }
}

Beszédes nevek

Keressük meg a legbeszédesebb neveket. Ha bizonytalanok vagyunk, próbáljunk meg több nevet is. Használjunk bátran hosszú neveket. A nevek megválasztásánál legyünk itt is következetesek.

Paraméterek

Az a legideálisabb ha egy függvénynek egyetlen paramétere sincs.

Előfordul, hogy van egy paraméterünk, amivel kapcsolatban valamilyen kérdésre szeretnénk választ adni, vagy azon egy műveletet szeretnénk elvégezni. A függvény nevében következetesen szét kell választani ezt két tevékenységet.

Vannak a jelzőparaméterek, amelyek használatát kerülni kell. A jelző paraméter, amikor például átadok egy logikai paramétert, amely megmondja, hogy amin művelete kell végezni az milyen állapotban van. Az ilyen függvények helyett írjunk két függvényt, amely mindkét állapotra megoldást nyújt.

Tegyük fel, hogy van egy függvényünk, ami képes PostgreSQL és MariaDB adatbázishoz kapcsolódni. Hogy melyikhez kapcsolódik egy állandóval jelezzük.

DatabaseCon.java
class DatabaseConn {
    public Connection connect(DatabaseType.PostgreSQL) {
       ...
    }
}

Az ilyen szerkezetek kerülendők. Írjunk helyette két külön függvényt. Az egyik PostgreSQL adatbázis kapcsolatához, a másik a MariaDB-hez.

Ha egy függvénynek 2-3 paraméternél többre van szüksége, csomagoljuk egy osztályba.

Mellékhatások

Ha egy művelet hatással van olyan változókra, objektumokra amely kívül esik tervezett célon, akkor azt mellékhatásnak nevezzük.

Adott egy függvény, ami MariaDB adatbázishoz kapcsolódik.

DatabaseCon.java
class Mariadb {
    boolean connected = false;
    public Connection connect() {
       ...
       connected = true;
    }
}

Matematikai értelemben 1), ha egy függvénynek nincs visszatérési értéke, biztosan van valami mellékhatása. Például megváltoztatja az objektum állapotát.

Nekünk most, fontosabb mi a függvény létrehozásának célja. Ha megváltoztatja egy objektum állapotát, az lehet csak hatás, ha ez volt a függvény létrehozásának célja. Ha visszaad valamit a függvény, akkor általában nem az a célja, hogy megváltoztasson valahol egy objektumot.

Kimeneti paraméterek

class Program01 {
    public static void main(String[] args) {
        StringBuffer msg = null;
        getMessage(msg);
        System.out.println(msg);
    }
    public static void getMessage(StringBuffer msg) {
        msg.append("Helló Világ");
    }
}

Irodalom

  • Robert C. Martin: Tiszta kód (2010, Budapest, KISKAPU)
oktatas/programozas/tisztakod.1630685091.txt.gz · Utolsó módosítás: 2021/09/03 18:04 szerkesztette: admin