java工廠模式,工廠模式和抽象工廠模式的區別

本文目錄一覽:

Java的工廠模式有哪一些,分別有什麼作用,一般用在哪些地方?

我簡單的說下,舉個例子,當我們的程序結構比較繁雜時,比如有100個類,而類中又有很多方法,這些方法之間都互相有依賴關係,也就是一個方法之間的某段邏輯處理需要用到另一個類中的代碼邏輯,這種時候對於整個程序而言是非常不利於開發的(我們需要考慮到很多類、方法之間的耦合問題),那麼就有一個概念了,也就是面對接口編程。通俗的說就是把類中的方法封裝起來,外部調用的人完全不需要考慮方法是如何實現的,但是這樣做也有一個不好的地方,我們的接口是不提供方法實現的,而需要在類中實現接口的方法。那麼問題產生了,我們在new接口對象的時候需要明確的知道他的實例類。

想像一下,如果程序在繼續龐大,接口非常多,接口實例類非常多,這樣又會產生我們之前的問題(我們需要考慮到很多類、方法之間的耦合問題)那麼這個時候就產生了一中設計思想,也就是工廠模式,這種模式的核心思想就是管理接口的實例對象,把接口和實例對象之間的關係封裝起來處理,外部需要用到某個接口的實例時,由工廠進行分配,而不需要關注具體是哪個實例。

如果你做到比較複雜的程序時你應該就能體會到了。

Java中常用的設計模式有哪些?請詳細說明一下工廠模式。

1.單例模式(有的書上說叫單態模式其實都一樣)

該模式主要目的是使內存中保持1個對象

2.工廠模式

該模式主要功能是統一提供實例對象的引用。看下面的例子:

public class Factory{

public ClassesDao getClassesDao(){

ClassesDao cd = new ClassesDaoImpl();

return cd;

}

}

interface ClassesDao{

public String getClassesName();

}

class ClassesDaoImpl implements ClassesDao {

public String getClassesName(){

System.out.println(“A班”);

}

}

class test

{

public static void main(String[] args){

Factory f = new Factory();

f.getClassesDao().getClassesName();

}

}

這個是最簡單的例子了,就是通過工廠方法通過接口獲取對象的引用

3.建造模式

該模式其實就是說,一個對象的組成可能有很多其他的對象一起組成的,比如說,一個對象的實現非常複雜,有很多的屬性,而這些屬性又是其他對象的引用,可能這些對象的引用又包括很多的對象引用。封裝這些複雜性,就可以使用建造模式。

4.門面模式

這個模式個人感覺像是Service層的一個翻版。比如Dao我們定義了很多持久化方法,我們通過Service層將Dao的原子方法組成業務邏輯,再通過方法向上層提供服務。門面模式道理其實是一樣的。

5.策略模式

這個模式是將行為的抽象,即當有幾個類有相似的方法,將其中通用的部分都提取出來,從而使擴展更容易。

java策略模式和工廠模式的區別

工廠模式是創建型模式

策略模式是行為性模式

一個關注對象創建

一個關注行為的封裝

策略模式就是定義一系列的算法,這些算法可以在需要的時候替換和擴展.工廠模式是生成型的模式,在你需要的時候構建具體的實例.

在下面的情況下應當考慮使用策略模式:

1. 如果在一個系統裏面有許多類,它們之間的區別僅在於它們的行為,那麼使用策略模式可以動態地讓一個對象在許多行為中選擇一種行為。

2.

一個系統需要動態地在幾種算法中選擇一種。那麼這些算法可以包裝到一個個的具體算法類裏面,而這些具體算法類都是一個抽象算法類的子類。換言之,這些具體

算法類均有統一的接口,由於多態性原則,客戶端可以選擇使用任何一個具體算法類,並只持有一個數據類型是抽象算法類的對象。

3. 一個系統的算法使用的數據不可以讓客戶端知道。策略模式可以避免讓客戶端涉及到不必要接觸到的複雜的和只與算法有關的數據。

4. 如果一個對象有很多的行為,如果不用恰當的模式,這些行為就只好使用多重的條件選擇語句來實現。此時,使用策略模式,把這些行為轉移到相應的具體策略類裏面,就可以避免使用難以維護的多重條件選擇語句,並體現面向對象設計的概念。

策略模式的優點和缺點

策略模式有很多優點和缺點。它的優點有:

1. 策略模式提供了管理相關的算法族的辦法。策略類的等級結構定義了一個算法或行為族。恰當使用繼承可以把公共的代碼移到父類裏面,從而避免重複的代碼。

2.

策略模式提供了可以替換繼承關係的辦法。繼承可以處理多種算法或行為。如果不是用策略模式,那麼使用算法或行為的環境類就可能會有一些子類,每一個子類提

供一個不同的算法或行為。但是,這樣一來算法或行為的使用者就和算法或行為本身混在一起。決定使用哪一種算法或採取哪一種行為的邏輯就和算法或行為的邏輯

混合在一起,從而不可能再獨立演化。繼承使得動態改變算法或行為變得不可能。

3. 使用策略模式可以避免使用多重條件轉移語句。多重轉移語句不易維護,它把採取哪一種算法或採取哪一種行為的邏輯與算法或行為的邏輯混合在一起,統統列在一個多重轉移語句裏面,比使用繼承的辦法還要原始和落後。

策略模式的缺點有:

1. 客戶端必須知道所有的策略類,並自行決定使用哪一個策略類。這就意味着客戶端必須理解這些算法的區別,以便適時選擇恰當的算法類。換言之,策略模式只適用於客戶端知道所有的算法或行為的情況。

2. 策略模式造成很多的策略類。有時候可以通過把依賴於環境的狀態保存到客戶端裏面,而將策略類設計成可共享的,這樣策略類實例可以被不同客戶端使用。換言之,可以使用享元模式來減少對象的數量。

策略模式與很多其它的模式都有着廣泛的聯繫。Strategy很容易和Bridge模式相混淆。雖然它們結構很相似,但它們卻是為解決不同的問題

而設計的。Strategy模式注重於算法的封裝,而Bridge模式注重於分離抽象和實現,為一個抽象體系提供不同的實現。Bridge模式與

Strategy模式都很好的體現了”Favor composite over inheritance”的觀點。

用java 編寫程序寫出簡單的工廠模式?

java中工廠模式分為:

簡單工廠模式(Simple Factory) 

2. 工廠方法模式(Factory Method) 

3. 抽象工廠模式(Abstract Factory)

每種方法的實現不同

提供一個簡單工廠模式的案例:

public abstract class Woman {

private String mySkill;

public String getMySkill() {

return mySkill;

}

public Woman() {

//System.out.println(“我是女人”);

}

public void setMySkill(String mySkill) {

this.mySkill = mySkill;

}

}

—————————-

public class LovelinessWoman extends Woman{

/*

* 可愛型女人

*/

  public LovelinessWoman()

  {

  String mySkill=”撒過嬌、出過軌、勾引領導下過水”;

      this.setMySkill(mySkill);

  }

}

—————————–

public class SteelinessWoman extends Woman{

/*

* 冷酷型女人

*/

  public SteelinessWoman()

  {

  String mySkill=”裝過神、弄過鬼,跟別人老公親過嘴”;

      this.setMySkill(mySkill);

  }

}

————————————–

public class WomanMakeFactory {

public Woman findWoman(int typeID) {

switch (typeID) {

case 1:

return new LovelinessWoman();

case 2:

return new VirtuousWoman();

case 3:

return new SteelinessWoman();

default:

return null;

}

}

public Woman findWoman(String type) throws ClassNotFoundException, InstantiationException, IllegalAccessException {

/*

* Type t = Type.GetType(“SimpleFactory.” + type);

* Woman wm =

* (Woman)Activator.CreateInstance(t); return wm;

*/

String string=”cn.jbit.design.simplefactory.”+type;

Class c = Class.forName(string);

Woman wm = (Woman) c.newInstance();

return wm;

}

}

————————-

調用

public class Test2 {

/**

* @param args

* @throws IllegalAccessException

* @throws InstantiationException

* @throws ClassNotFoundException

*/

public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException {

Scanner input=new Scanner(System.in);

boolean sel=false;

do {

System.out.println(“請選擇你要找的女人的類型”);

System.out.println(“LovelinessWoman:可愛型女人 VirtuousWoman:善良型女人 SteelinessWoman:冷酷型女人”);

String typeid=input.next();

       WomanMakeFactory factory = new WomanMakeFactory();

       Woman wm=factory.findWoman(typeid);

       System.out.println(“該類型女人的新標準:”);

       System.out.println(wm.getMySkill());

     

       System.out.println(“還想看看別的類型嗎?y代表想,n代表再也不想了”);

     

       sel=input.next().equals(“y”);

} while (sel);

}

}

java工廠模式,懂的人進

舉兩個例子以快速明白Java中的簡單工廠模式:

女媧摶土造人

話說:「天地開闢,未有人民,女媧摶土為人。」女媧需要用土造出一個個的人,但在女媧造出人之前,人的概念只存在於女媧的思想裏面。

女媧造人,這就是簡單工廠模式的應用。

首先,在這個造人的思想裏面,有幾個重要的角色:女媧本身、抽象的人的概念和女媧所造出的一個個具體的人。

1.)女媧是一個工廠類,也就是簡單工廠模式的核心角色。

2.)具休的一個個的人,包括張三,李四等。這些人便是簡單工廠模式裏面的具體產品角色

3.)抽象的人是最早只存在於女媧的頭腦里的一個想法,女媧按照這個想法造出的一個個具體的人,便都符合這個抽象的人的定義。換言之,這個抽象的想法規定了所有具體的人必須都有的接口(特徵或者功能)

 其UML類圖出下所示:

理解了上面的這些東西,再來理解下面的例子,對照理解,相信看完這篇文章,便對java簡單工廠模式有一個很好的理解:

有一個農場公司,專門向市場銷售各類水果,在這個系統里需要描述下列水果:

 葡萄 Grape

 草莓 Stuawberry

 蘋果 Apple

水果與其他植物不同,最終可以採摘食用,那麼一個自然的做法是建立一個各種水果都適用的接口,以便與其他農場里的植物區分開來,

此時,則是為水果類聲明了一個接口,表現在代碼上:

1 public interface Fruit {

2 // 生長

3 void grow();

4 // 收穫

5 void harvest();

6 // 種植

7 void plant();

8 }

9

10

水果接口規定出所有的水果必須實現的接口,包括任何水果類必須具備的方法plant(),grow(),和harvest();

Apple類是水果類的一種,因此它實現了水果接口所聲明的所有方法。另處,由於蘋果是多年生植物,因此多出一個treeAge性質,描述蘋果的樹齡。代碼如下所示:

package fac;

public class Apple implements Fruit { // 通過implements實現接口Fruit

private int treeAge;

public void grow() {

log( ” Apple is growing ” );

}

public void harvest() {

log( ” Apple has been harvested ” );

}

public void plant() {

log( ” Apple ha been planted ” );

}

public static void log(String msg) {

System.out.println(msg);

}

public int getTreeAge() {

return treeAge;

}

public void setTreeAge( int treeAge) {

this .treeAge = treeAge;

}

}

同理,葡萄 Grape:

package fac;

public class Grape implements Fruit{

private boolean seedless;

public void grow(){

log(“Grape is growing.”);

}

public void harvest(){

log(“Grape has been harvested”);

}

public void plant(){

log(“Grape ha been planted”);

}

public static void log(String msg){

System.out.println(msg);

}

public boolean isSeedless() {

return seedless;

}

public void setSeedless(boolean seedless) {

this.seedless = seedless;

}

}

草莓 Stuawberry:

package fac;

public class Strawberry implements Fruit{

public void grow(){

log(“Strawberry is growing”);

}

public void harvest(){

log(“Strawberry has been harvested”);

}

public void plant(){

log(“Strawberry has been planted”);

}

public static void log(String msg){

System.out.println(msg);

}

}

農場園丁也是系統的一部分,由一個類來代表,FruitGardener類,代碼如下:

package fac;

public class FruitGardener{

public static Fruit factory(String which)throws Exception{

if(which.equalsIgnoreCase(“apple”)){

return new Apple();

}else if(which.equalsIgnoreCase(“strawberry”)){

return new Strawberry();

}else if (which.equalsIgnoreCase(“grape”)){

return new Grape();

}else{

throw new Exception(“Bad fruit request”);

}

}

}

這時有人來果園玩,和園丁說,給我們介紹下你的水果吧。於是園丁:

package fac;

public class People {

public static void main(String[] args) throws Exception {

FruitGardener fg=new FruitGardener();

Fruit ap=fg.factory(“Apple”);

ap.grow();

Fruit gp=fg.factory(“Grape”);

gp.plant();

Fruit dd=fg.factory(“ddd”);//拋出Bad fruit request異常

}

}

(註:以上代碼在JDK5.0,Myeclise3.2下編譯通過)

類比兩個例子,園丁就相當於女媧,而水果就相當於具體的人,接口水果類就相當於存在於類女媧思想里的人的抽象概念。

由以上兩個例子可得出,簡單工廠模式需要由以下角色組成:

接口

接口的實現類(簡單工廠模式裏面的具體產品角色)

工廠

理解了以下兩個例子,再來看第三個例子:

注意對比以下三個實例的不同

實例1:

package org.jzkangta.factorydemo01;

//定義接口

interface Car{

public void run();

public void stop();

}

//具體實現類

class Benz implements Car{

public void run(){

System.out.println(“Benz開始啟動了。。。。。”);

}

public void stop(){

System.out.println(“Benz停車了。。。。。”);

}

}

//具體實現類

class Ford implements Car{

public void run(){

System.out.println(“Ford開始啟動了。。。”);

}

public void stop(){

System.out.println(“Ford停車了。。。。”);

}

}

//工廠

class Factory{

public static Car getCarInstance(){

return new Ford();

}

}

public class FactoryDemo01 {

public static void main(String[] args) {

Car c=Factory.getCarInstance();

c.run();

c.stop();

}

}

實例二:

package fac;

//定義接口

interface Car{

public void run();

public void stop();

}

//具體實現類

class Benz implements Car{

public void run(){

System.out.println(“Benz開始啟動了。。。。。”);

}

public void stop(){

System.out.println(“Benz停車了。。。。。”);

}

}

class Ford implements Car{

public void run(){

System.out.println(“Ford開始啟動了。。。”);

}

public void stop(){

System.out.println(“Ford停車了。。。。”);

}

}

//工廠

class Factory{

public static Car getCarInstance(String type){

Car c=null;

if(“Benz”.equals(type)){

c=new Benz();

}

if(“Ford”.equals(type)){

c=new Ford();

}

return c;

}

}

public class FactoryDemo02 {

public static void main(String[] args) {

Car c=Factory.getCarInstance(“Benz”);

if(c!=null){

c.run();

c.stop();

}else{

System.out.println(“造不了這種汽車。。。”);

}

}

}

實例三:

interface Car{

public void run();

public void stop();

}

class Benz implements Car{

public void run(){

System.out.println(“Benz開始啟動了。。。。。”);

}

public void stop(){

System.out.println(“Benz停車了。。。。。”);

}

}

class Ford implements Car{

public void run(){

System.out.println(“Ford開始啟動了。。。”);

}

public void stop(){

System.out.println(“Ford停車了。。。。”);

}

}

class Toyota implements Car{

public void run(){

System.out.println(“Toyota開始啟動了。。。”);

}

public void stop(){

System.out.println(“Toyota停車了。。。。”);

}

}

class Factory{

public static Car getCarInstance(String type){

Car c=null;

try {

c=(Car)Class.forName(“org.jzkangta.factorydemo03.”+type).newInstance();//利用反射得到汽車類型 

} catch (InstantiationException e) {

// TODO Auto-generated catch block

e.printStackTrace();

} catch (IllegalAccessException e) {

// TODO Auto-generated catch block

e.printStackTrace();

} catch (ClassNotFoundException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

return c;

}

}

public class FactoryDemo03 {

public static void main(String[] args) {

Car c=Factory.getCarInstance(“Toyota”);

if(c!=null){

c.run();

c.stop();

}else{

System.out.println(“造不了這種汽車。。。”);

}

}

}

對比三個實例:

實例一,雖然實現了簡單工廠,但每次只能得到一種汽車,如果我們想換一種,就得修改工廠,太不方便,而實例二則改變了這種情況,便得我們可以按照我們的需要更換汽車,但我們所更換的汽車必須是實現類中有的,如果我們想要增加一種汽車的時候,我們還是得更改工廠,通過改進,實例三利用反射機制,得到汽車類型,這樣當我們需要增加一種新的汽車時,就無需要再修改工廠,而只需要增加要實現的類即可。也就是說要增加什麼樣的汽車直接增加這個汽車的類即可,而無需改變工廠。從而達到了工廠分離的效果。

原創文章,作者:KNND,如若轉載,請註明出處:https://www.506064.com/zh-hk/n/139285.html

(0)
打賞 微信掃一掃 微信掃一掃 支付寶掃一掃 支付寶掃一掃
KNND的頭像KNND
上一篇 2024-10-04 00:22
下一篇 2024-10-04 00:22

相關推薦

  • Python中new和init的區別

    new和init都是Python中常用的魔法方法,它們分別負責對象的創建和初始化,本文將從多個角度詳細闡述它們的區別。 一、創建對象 new方法是用來創建一個對象的,它是一個類級別…

    編程 2025-04-29
  • Sublime Test與Python的區別

    Sublime Text是一款流行的文本編輯器,而Python是一種廣泛使用的編程語言。雖然Sublime Text可以用於編寫Python代碼,但它們之間有很多不同之處。接下來從…

    編程 2025-04-29
  • Shell腳本與Python腳本的區別

    本文將從多個方面對Shell腳本與Python腳本的區別做詳細的闡述。 一、語法差異 Shell腳本和Python腳本的語法存在明顯差異。 Shell腳本是一種基於字符命令行的語言…

    編程 2025-04-29
  • Python中while語句和for語句的區別

    while語句和for語句是Python中兩種常見的循環語句,它們都可以用於重複執行一段代碼。然而,它們的語法和適用場景有所不同。本文將從多個方面詳細闡述Python中while語…

    編程 2025-04-29
  • Web程序和桌面程序的區別

    Web程序和桌面程序都是進行軟件開發的方式,但是它們之間存在很大的區別。本文將從多角度進行闡述。 一、運行方式 Web程序運行於互聯網上,用戶可以通過使用瀏覽器來訪問它。而桌面程序…

    編程 2025-04-29
  • TensorFlow和Python的區別

    TensorFlow和Python是現如今最受歡迎的機器學習平台和編程語言。雖然兩者都處於機器學習領域的主流陣營,但它們有很多區別。本文將從多個方面對TensorFlow和Pyth…

    編程 2025-04-28
  • 麥語言與Python的區別

    麥語言和Python都是非常受歡迎的編程語言。它們各自有自己的優缺點和適合的應用場景。本文將從語言特性、語法、生態系統等多個方面,對麥語言和Python進行詳細比較和闡述。 一、語…

    編程 2025-04-28
  • MySQL bigint與long的區別

    本文將從數據類型定義、存儲空間、數據範圍、計算效率、應用場景五個方面詳細闡述MySQL bigint與long的區別。 一、數據類型定義 bigint在MySQL中是一種有符號的整…

    編程 2025-04-28
  • Python與C語言的區別和聯繫

    Python與C語言是兩種常用的編程語言,雖然兩者都可以用於編寫軟件程序,但是它們之間有很多不同之處。本文將從多個方面對Python與C語言的區別和聯繫進行詳細的闡述。 一、語法特…

    編程 2025-04-28
  • 手機安全模式怎麼解除?

    安全模式是一種手機自身的保護模式,它會禁用第三方應用程序並使用僅限基本系統功能。但有時候,安全模式會使你無法使用手機上的一些重要功能。如果你想解除手機安全模式,可以嘗試以下方法: …

    編程 2025-04-28

發表回復

登錄後才能評論