<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    隨筆 - 11  文章 - 33  trackbacks - 0
    <2007年9月>
    2627282930311
    2345678
    9101112131415
    16171819202122
    23242526272829
    30123456

    常用鏈接

    留言簿(1)

    隨筆分類

    隨筆檔案

    文章檔案

    搜索

    •  

    最新隨筆

    最新評(píng)論

    閱讀排行榜

    評(píng)論排行榜

    本文假定讀者已經(jīng)了解有關(guān)正方形不是長(zhǎng)方形的相關(guān)內(nèi)容。
            
            之前人們討論的正方形長(zhǎng)方形的問(wèn)題的關(guān)鍵在哪里?我覺(jué)得就在于改動(dòng)長(zhǎng)方形的邊的長(zhǎng)度。我們可以這么考慮一下,一個(gè)長(zhǎng)方形的instance的邊長(zhǎng)應(yīng)該是可變的嗎?我覺(jué)得一旦一個(gè)長(zhǎng)方形的邊長(zhǎng)改變之后它就成了另一個(gè)長(zhǎng)方形了(一個(gè)新的instance)。所以長(zhǎng)方形類里面不應(yīng)該有改變其邊長(zhǎng)的方法,一個(gè)長(zhǎng)方形實(shí)例各個(gè)的邊長(zhǎng)應(yīng)當(dāng)在new它的時(shí)候確定下來(lái),并且它們應(yīng)當(dāng)是immutable的。基于這種考慮,我設(shè)計(jì)的長(zhǎng)方形和正方形的類如下所示:
    //長(zhǎng)方形
    public class Rectangle {
      private final int width;
      private final int height;
     
      public Rectangle(int width, int height) {
        this.width = width;
        this.height = height;
      }
     
      public int getWidth() {
        return width;
      }

      public int getHeight() {
        return height;
      }
     
      public int getArea() {
        return width*height;
      }
    }

    //正方形
    public class Square extends Rectangle{
      private final int side;
     
      public Square(int side) {
        super(side, side);
        this.side = side;
      }
     
      public int getSide() {
        return side;
      }
    }

            這種繼承關(guān)系就既符合現(xiàn)實(shí)中的父子關(guān)系也遵循LSP。之所以這么設(shè)計(jì),我的想法是一個(gè)類所具有的方法不應(yīng)當(dāng)能夠改變其本質(zhì)。比如有一個(gè)Men類,它可以有eat(),sleep(),work(),makeLovewith(Person p)方法,但是如果你在里面定義denatureToWomen(),denatureToEunuch()就很不恰當(dāng)了,因?yàn)檫@改變了其本質(zhì),導(dǎo)致這個(gè)Men的實(shí)例不再屬于Men類(至少已經(jīng)和現(xiàn)實(shí)不吻合)了。除非這兩個(gè)方法不能改變?cè)搶?shí)例本質(zhì),否則在Men里面定義這兩個(gè)方法本身就是有問(wèn)題的。不過(guò)如果用下面這種方式定義也許可行:
    public Women denatureToWomen() {
      Women w = new Women();
      //set attributes here
      return w;
    }

    public Eunuch denatureToEunuch() {
      Eunuch e = new Eunuch();
      //set attributes here
      return e;
    }

    這樣一來(lái),調(diào)用denatureToWomen()會(huì)產(chǎn)生一個(gè)新的實(shí)例,原來(lái)的那個(gè)Men實(shí)例依然存在,這和現(xiàn)實(shí)生活依然不吻合,現(xiàn)實(shí)生活中一個(gè)實(shí)例不光可以上型(upcast),還可以平行型,寒。。。

    總之一句話,一個(gè)類的方法不應(yīng)該改變其實(shí)例的本質(zhì)。

    posted on 2007-09-20 16:33 teasp 閱讀(2729) 評(píng)論(13)  編輯  收藏 所屬分類: Java學(xué)習(xí)

    FeedBack:
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 16:43 千里冰封
    呵呵,有意思  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 18:29 GandofYan
    new Square (4,5);

    會(huì)有什么結(jié)果呢?  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 18:45 teasp
    @GandofYan
    兄弟啊,Square只有一個(gè)構(gòu)造方法,你說(shuō)的這句有語(yǔ)法錯(cuò)誤哦。  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 19:55 GandofYan
    @teasp


    哦,sorry,我一直以為構(gòu)造方法子類是繼承的
    我說(shuō)錯(cuò)了:)  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 20:38 黑蝙蝠
    makeLovewith你取的方法名字真酷 呵呵

    還是沒(méi)明白你到底想表達(dá)什么》??  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 21:33 teasp
    @黑蝙蝠

    呵呵,我不知道你有沒(méi)有看過(guò)關(guān)于正方形不是長(zhǎng)方形的討論,網(wǎng)上有的,另外《Java與模式》里面第79頁(yè)左右就是講這個(gè)問(wèn)題的。如果你看過(guò)相關(guān)的內(nèi)容,應(yīng)該能明白我要表達(dá)的意思了。  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-20 21:49 teasp
    沒(méi)看過(guò)相關(guān)討論的可以看看這個(gè)先:

    長(zhǎng)方形有二個(gè)屬性長(zhǎng)和寬。并有一個(gè)設(shè)置長(zhǎng)的方法和設(shè)置寬的方法,還有一個(gè)求面積的方法.
    像下面
    private int length;
    private int width;
    public void setLength(int lenght) {
    this.length = lenght;
    }
    public void setWidth(int width) {
    this.width= width;
    }
    public int getArea() {
    return this.length * this.width;
    }
    如果說(shuō)正方形是長(zhǎng)方形的子類。為了保證正方形長(zhǎng)和寬相等,那對(duì)應(yīng)于正方形的二設(shè)置長(zhǎng)寬的個(gè)方法就得改成
    public void setLength(int lenght) {
    this.length = lenght;
    this.width= lenght;
    }
    public void setWidth(int width) {
    this.length = width;
    this.width= width;
    }
    那我們想想用戶使用時(shí)候的情景。 我們都知道長(zhǎng)方形的面積等于長(zhǎng)與寬的積。那當(dāng)我們用長(zhǎng)方形的時(shí)候我們會(huì)這樣用
    Rectangle rectangle = new Rectangle();
    rectangle.setLength(5);
    rectangle.setWidth(4);
    我們想知道面積是多少我們就可以
    rectangle.getArea();
    得到的是20,當(dāng)然結(jié)果是非常正確的。
    但想想如果我們把一個(gè)正方形的實(shí)例給用戶用的時(shí)候會(huì)怎么樣
    Rectangle rectangle = new Square(); //注意,這里體顯代換原則。用戶根本不知道真正的實(shí)例是正方形,用戶只知道長(zhǎng)方形的事情。
    rectangle.setLength(5);
    rectangle.setWidth(4);
    我們想知道面積是多少我們就可以
    rectangle.getArea();
    得到的結(jié)果卻是 16 ,這違背了長(zhǎng)方形的面積是長(zhǎng)與寬之積的原則。用戶就不會(huì)明白為什么我設(shè)置了長(zhǎng)是5寬是4得到的答案卻是16 ?? 與前提不符
    所以正方形不能代替長(zhǎng)方形出現(xiàn)在這個(gè)地方。
    也就是說(shuō)正方形不應(yīng)當(dāng)看作是長(zhǎng)方形的子類。
      回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-21 10:27 辛科
    認(rèn)同樓主  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-21 16:38 dominobaby
    繼承是泛化,是擴(kuò)展,結(jié)果是:女人不是人,但翠花是人!
    作者的看法確實(shí)可取,邊長(zhǎng)似乎確實(shí)是方形的標(biāo)志性。
    但是這樣的話,哪些作為不可變量很難確定。比如:矮子是不是人?想一個(gè)矮子類,就得把高矮也定為不可變量,可是這就跟人的生長(zhǎng)特性矛盾了。
      回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-21 17:51 teasp
    樓上說(shuō)得很有道理,最關(guān)鍵的問(wèn)題是我們不知道哪些特性才是一個(gè)類的標(biāo)志。因?yàn)楝F(xiàn)實(shí)世界太復(fù)雜了,簡(jiǎn)直不可模仿  回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-23 20:21 zenny_chen
    我認(rèn)為將正方形作為長(zhǎng)方形的子類本身是一個(gè)錯(cuò)誤的概念。
    實(shí)際上我們應(yīng)該將面向?qū)ο笾械睦^承與離散數(shù)學(xué)的集合論聯(lián)系起來(lái):
    例如有集合A={a, b, c}, B={a, b}。這里顯然B是A的子集。然而如果用面向?qū)ο蟮姆椒▽⑦@兩個(gè)集合構(gòu)造為兩個(gè)具有繼承關(guān)系的類結(jié)構(gòu)的話很顯然,應(yīng)該將集合B作為父類而將集合A作為B的子類。
    因此,像public class Square extends Rectangle這種寫(xiě)法欠妥。作為正方形其元素就只要一個(gè)邊長(zhǎng),而矩形則要兩個(gè)。因此,根據(jù)上面的集合,可以列出Square={a}, Rectangle={a, b}。很顯然,應(yīng)該將正方形作為父類,而矩形作為正方形的子類。(當(dāng)然,作為集合元素應(yīng)該為集合類型,而不是組合。不過(guò)在軟件設(shè)計(jì)建模上暫且就如此表示)。

    在做面向?qū)ο蟮脑O(shè)計(jì)時(shí),不應(yīng)該死板地去看待現(xiàn)有邏輯,盡管我們一直認(rèn)為正方形是矩形的一個(gè)子類(特殊類)。但根據(jù)繼承的概念——子類繼承父類的所有屬性和操作這一概念,在很多時(shí)候集合中的子集關(guān)系與面向?qū)ο笾械睦^承關(guān)系是相反的。

      回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-23 20:26 zenny_chen
    對(duì)了。在這里說(shuō)明一下,上面提到的“Square={a}, Rectangle={a, b}”中Square和Rectangle是指正方形與矩形的邊長(zhǎng)集,而不是指正方形與矩形的集合。
      回復(fù)  更多評(píng)論
      
    # re: 正方形不是長(zhǎng)方形的終極解決辦法 2007-09-24 10:45 真的遵循LSP?
    長(zhǎng)方形在這里只是舉個(gè)例子 ,在一個(gè)類中改變一個(gè)類的屬性的方法是很正常的需求,既然原來(lái)的結(jié)論:
    "也就是說(shuō)正方形不應(yīng)當(dāng)看作是長(zhǎng)方形的子類。 "

    那正方形類就不應(yīng)改繼承長(zhǎng)方形類.  回復(fù)  更多評(píng)論
      
    主站蜘蛛池模板: 亚洲精品国精品久久99热| 亚洲伦理一二三四| 欧洲精品99毛片免费高清观看| 18gay台湾男同亚洲男同| 无限动漫网在线观看免费| 精品亚洲视频在线| 亚洲va无码手机在线电影| 性做久久久久久免费观看| 99精品视频免费| 亚洲 欧洲 日韩 综合在线| 国产亚洲成人在线播放va| 噼里啪啦免费观看高清动漫4| 一级黄色毛片免费看| 亚洲一级毛片中文字幕| 亚洲综合伊人久久综合| 成全视频免费高清| 日韩免费的视频在线观看香蕉| 亚洲国产精品无码中文lv| 久久精品国产亚洲av四虎| 国产免费拔擦拔擦8x| 久久久久免费看成人影片| 一级黄色片免费观看| 亚洲色成人WWW永久在线观看| 亚洲成AV人片在线观看WWW| 国产a级特黄的片子视频免费| xxxx日本免费| aa级女人大片喷水视频免费| 国产AV无码专区亚洲AV蜜芽| 亚洲性色成人av天堂| 国产精品亚洲A∨天堂不卡 | 吃奶摸下高潮60分钟免费视频| 无码国产精品一区二区免费3p| 男人扒开添女人下部免费视频| 亚洲午夜电影在线观看| 亚洲a在线视频视频| 久久亚洲AV无码西西人体| 国产美女无遮挡免费视频| 无人在线观看完整免费版视频| 一级毛片免费观看| 中文在线观看国语高清免费| 一级特黄a免费大片|