Фабрични методи

Въпрос: Докато преминавах през „Полиморфизъм в най-чистата му форма“, видях непознатия термин фабричен метод. Бихте ли описали какво е фабричен метод и как можете да го използвам?

О: Нека разгледаме пример.

Всяка програма се нуждае от начин за докладване на грешки. Помислете за следния интерфейс:

Листинг 1

публичен интерфейс Trace {// включва и изключва отстраняване на грешки public void setDebug (логическо отстраняване на грешки); // изписване на съобщение за отстраняване на грешки public void debug (String message); // изписване на съобщение за грешка public void error (низ съобщение); }

Да предположим, че сте написали две реализации. Една реализация (Листинг 2) записва съобщенията в командния ред, докато друга (Листинг 3) ги записва във файл.

Листинг 2

публичният клас FileTrace изпълнява Trace {private java.io.PrintWriter pw; частно логическо отстраняване на грешки; public FileTrace () хвърля java.io.IOException {// истински FileTrace ще трябва да получи името на файла някъде // за пример ще го кодирам твърдо pw = new java.io.PrintWriter (new java.io.FileWriter (" c: \ trace.log ")); } public void setDebug (boolean debug) {this.debug = debug; } public void debug (String message) {if (debug) {// print only if debug is true pw.println ("DEBUG:" + message); pw.flush (); }} public void error (String message) {// винаги отпечатва грешки pw.println ("ГРЕШКА:" + съобщение); pw.flush (); }}

Листинг 3

публичният клас SystemTrace изпълнява Trace {частно булево отстраняване на грешки; public void setDebug (boolean debug) {this.debug = debug; } public void debug (String message) {if (debug) {// print only if debug is true System.out.println ("DEBUG:" + message); }} public void error (String message) {// винаги разпечатва грешки System.out.println ("ГРЕШКА:" + съобщение); }}

За да използвате някой от тези класове, ще трябва да направите следното:

Листинг 4

// ... някакъв код ... SystemTrace log = new SystemTrace (); // ... код ... log.debug ("въвеждане на дневник"); // ... и т.н. ...

Сега, ако искате да промените Traceизпълнението, което вашата програма използва, ще трябва да редактирате всеки клас, който създава екземпляр на Traceизпълнение. В зависимост от броя на класовете, които използват Trace, може да отнеме много работа, за да направите промяната. Освен това искате да избягвате да променяте класовете си колкото е възможно повече.

Фабричният метод ни позволява да бъдем много по-умни относно това как нашите класове получават Traceекземпляри за изпълнение:

Листинг 5

публичен клас TraceFactory {публичен статичен Trace getTrace () {върне нов SystemTrace (); }}

getTrace()е фабричен метод. Сега, когато искате да получите препратка към a Trace, можете просто да се обадите TraceFactory.getTrace():

Листинг 6

// ... някакъв код ... Trace log = new TraceFactory.getTrace (); // ... код ... log.debug ("въвеждане на дневник"); // ... и т.н. ...

Използването на фабричен метод за получаване на екземпляр може да ви спести много работа по-късно. В горния код TraceFactoryвръща SystemTraceекземпляри. Представете си отново, че вашите изисквания се променят и че трябва да запишете съобщенията си във файл. Ако обаче използвате фабричен метод за получаване на вашия екземпляр, трябва да направите само една промяна в един клас, за да отговорите на новите изисквания. Не е необходимо да правите промени във всеки клас, който използва Trace. Вместо това можете просто да предефинирате getTrace():

Листинг 7

публичен клас TraceFactory {публичен статичен Trace getTrace () {try {върне нов FileTrace (); } catch (java.io.IOException ex) {Проследяване t = нов SystemTrace (); t.error ("не може да се създаде екземпляр FileTrace:" + ex.getMessage ()); връщане t; }}}

Освен това фабричните методи се оказват полезни, когато не сте сигурни каква конкретна реализация на клас да създадете. Вместо това можете да оставите тези подробности на фабричния метод.

В горните примери вашата програма не знаеше дали да създава FileTraceили SystemTraceекземпляри. Вместо това можете да програмирате вашите обекти просто да използват Traceи да оставите инстанцирането на конкретната реализация на фабричен метод.

Тони Синтес е главен консултант в BroadVision. Сертифициран от Sun софтуер за Java 1.1 и разработчик на Java 2, той работи с Java от 1997 г.

Научете повече за тази тема

  • Първата спирка за всички ваши нужди от модели може да бъде намерена в прочутите дизайнерски модели на Gang of Four , Eric Gamma, Richard Helm, Ralph Johnson, John Vlissides (Addison-Wesley, 1995)

    //www.amazon.com/exec/obidos/ASIN/0201633612/javaworld

  • Искам още? Вижте индекса за въпроси и отговори на Java за пълния каталог с въпроси и отговори

    //www.javaworld.com/javaworld/javaqa/javaqa-index.html

  • За над 100 задълбочени съвети Java от някои от най-добрите умове в бизнеса, визита JavaWorld " и Java Съвети индекс

    //www.javaworld.com/javatips/jw-javatips.index.html

  • За повече статии, насочени към нови програмисти на Java, посетете раздела Въведение в Тематичния индекс на JavaWorld

    //www.javaworld.com/javaworld/topicalindex/jw-ti-introlevel.html

  • Говорете в дискусията за начинаещи Java

    //www.itworld.com/jump/jw-javaqa/forums.itworld.com/[email protected]@.ee6b804/1195!skip=1125

  • Получавайте седмични съвети за програмиране на Java, като се абонирате за нашия безплатен бюлетин по електронна поща за Java Tutor

    //reg.itworld.com/cgi-bin/subcontent12.cgi

Тази история „Фабрични методи“ първоначално е публикувана от JavaWorld.