A számítógép-programozásban előfordulhatnak olyan elemek, melyek mindig együtt mozognak. A primitívmániához hasonló, azonban itt az együtt mozgás következetes, és nemcsak primitívek tartozhatnak az adatlabdához. Az adatlabda tagjai gyakran összefüggenek, szorosan kapcsolódnak egymáshoz, és eredményként is együtt jelennek meg. Osztály szintű kódszagnak számít, ami gyenge minőségű forráskódra utalhat.

Logikailag összetartozó adatokról feltételezhető, hogy adatlabdát alkotnak. Úgy vizsgálható, hogy eltávolítjuk egyik-másik tagját, és megnézzük, hogy a maradéknak van-e értelme. Ha nincs, akkor ez arra mutat, hogy létre kell hozni egy új osztályt, melyből konstruált objektumok tartalmazzák az adatlabda tartalmát.

Refraktorálás

Általában az adatlabdák refraktorálásra szorulnak. Az adatlabdák jelenléte gyenge szoftverdizájnra mutat, mivel ezeket az összetartozó tagokat formálisan is egy objektumba kellene rakni, és ahelyett, hogy a tagokat adnánk át újra és újra, elegendő lenne az objektumot átadni. Ezzel lerövidülne a kód, szervezettebbé, olvashatóbbá, debugolhatóbbá válna.

Az adatlabdából könnyen adat osztály válhat, ha nem gyűjtünk hozzá metódusokat. Emiatt szükség lehet külön ellenőrizni a kliens kódot. Az osztály létrehozása bátorít is erre. Ezzel szemben, ha az adatok nincsenek együtt, akkor kevéssé fáradoznak a hozzájuk tartozó metódusok összegyűjtésével. Az objektumorientált programozás egyik fontos elve az egységbe zárás, ami azt jelenti, hogy az összetartozó adatokat és függvényeket egy helyre csoportosítja.

Egy hosszú paraméterlista még nem feltétlenül utal adatlabdára, mivel annak feltétele, hogy a tagok logikailag összetartozzanak. Habár ritkán fordul elő, megtörténhet, hogy egy metódus hat vagy még több, logikailag nem összetartozó adatot vesz át, melyekből nem célszerű egy objektumot csinálni. Ez arra utal, hogy a metódus túl sok mindent akar csinálni, és szét kellene tagolni, hogy ne kelljen túl sok paraméter.

Az adatlabdák refraktorálása eszközökkel segíthetők. Sok IDE-nek van erre eszköze, többnyire "Extract Class" néven, ami automatikusan elvégzi a műveletet. Ez növeli a megbízhatóságot és csökkenti a költséget, ezzel nagyon leegyszerűsíti a megoldást. Példák C# Refraktorálás előtt: public void AddCoords(int x, int y, int z) { /* … */ }

Refraktorálás után: public void AddCoords(Coords coords) { /* … */ }

public class Coords { public Coords(int x, int y, int z)

X = x; Y = y; Z = z;

public int X { get; } public int Y { get; } public int Z { get; } } Java public static void main(String args[]) { String firstName = args; String lastName = args; Integer age = new Integer(args); String gender = args; String occupation = args; String city = args; welcomeNew(firstName, lastName, age, gender, occupation, city); }

public static void welcomeNew(String firstName, String lastName, Integer age, String gender, String occupation, String city) { System.out.printf("Welcome %s %s, a %d-year-old %s from %s who works as a%s\n",firstName, lastName, age, gender, city, occupation); }

Az előző példában a változók csoportosíthatók egyetlen "Person" objektumba, ami önmagában átadható. Em,ellett a programozó felismerheti, hogy a welcomeNew metódusnak jobb helye lenne a Person osztályban, majd további releváns akciókat találhat a Person osztállyal kapcsolatban. Például a kód így refraktorálható és bővíthető:

public static void main(String args[]) { String firstName = args; String lastName = args; Integer age = new Integer(args); String gender = args; String occupation = args; String city = args;

Person joe = new Person(firstName, lastName, age, gender, occupation, city); joe.welcomeNew(); joe.work(); }

private static class Person { /* All parameters have been moved to the new Person class where they are properly grouped and encapsulated */ String firstName; String lastName; Integer age; String gender; String occupation; String city;

public Person(String firstName, String lastName, Integer age, String gender, String occupation, String city) { this.firstName = firstName; this.lastName = lastName; this.age = age; this.gender = gender; this.occupation = occupation; this.city = city;

/* Existing functionality relating to the data can also be incorporated into the new class, reducing the risk of scope collision */ public void welcomeNew() { System.out.printf("Welcome %s %s, a %d-year-old %s from %s who works as a%s\n", firstName, lastName, age, gender, city, occupation);

/* Additionally, the new class may be an opportunity for new functionality to be added */ public void work() { System.out.printf("This is %s working hard on %s in %s", firstName, occupation, city);

Habár ezzel megnőtt a kód hossza, most a Person érthetőbben adható át objektumként, mint mezők csomagjaként. Emellett most már lehetőség van arra, hogy a kapcsolódó metódusokat áttegyük ebbe az osztályba. Nem lesz szükségük arra, hogy a tagokat egyenként átvegyék, hiszen azokat az objektum tárolja.

Jegyzetek = Forrás Refractoring Guru Fordítás

Kategória:Programozási antiminták