zoukankan      html  css  js  c++  java
  • 【Effective Java】6、使用复合优先于使用继承

    这个,不管是什么书都会这样说,因为常常我们并不需要继承,而只是想把类进行一定的扩展,而我们想扩展的属性或方法对应的类都有,这个时候如果两者是is a的关系,这种关系是确实存在的,那么就可以使用继承,不然一般都是建议使用复合。

    如果我们队一个类进行继承的时候,我们如果对其内部的逻辑并不十分了解的时候,直接继承的结果就是可能有些方法是类自己内部调用的,而我们在继承这个方法的时候,可能会覆盖某些方法,或者重载某些方法,或者加上了一些自己的逻辑,这样就会吧原来的逻辑和我们自己的逻辑混杂起来,并且如果继承的类内部有使用这个类的话,那么就会调用我们自己写的部分逻辑,那么结果就变得不可预料了

    这里的建议是使用包装类模式

    package cn.xf.cp.ch02.item16;
    
    import java.util.Collection;
    import java.util.Iterator;
    import java.util.Set;
    
    public class ForwardingSet<E> implements Set<E>
    {
        
        /**
         * 这个类作为转发类,内部通过复合的方式把set作为一个组件
         */
        private final Set<E> s;
        
        public ForwardingSet(Set<E> s)
        {
            this.s = s;
        }
        
        @Override
        public int size()
        {
            return s.size();
        }
    
        @Override
        public boolean isEmpty()
        {
            return s.isEmpty();
        }
    
        @Override
        public boolean contains(Object o)
        {
            return s.contains(o);
        }
    
        @Override
        public Iterator<E> iterator()
        {
            return s.iterator();
        }
    
        @Override
        public Object[] toArray()
        {
            return s.toArray();
        }
    
        @Override
        public <T> T[] toArray(T[] a)
        {
            return s.toArray(a);
        }
    
        @Override
        public boolean add(E e)
        {
            return s.add(e);
        }
    
        @Override
        public boolean remove(Object o)
        {
            return s.remove(o);
        }
    
        @Override
        public boolean containsAll(Collection<?> c)
        {
            return s.containsAll(c);
        }
    
        @Override
        public boolean addAll(Collection<? extends E> c)
        {
            return s.addAll(c);
        }
    
        @Override
        public boolean retainAll(Collection<?> c)
        {
            return s.retainAll(c);
        }
    
        @Override
        public boolean removeAll(Collection<?> c)
        {
            return s.removeAll(c);
        }
    
        @Override
        public void clear()
        {
            s.clear();
        }
    
    }

    这样,我们在每个方法中调用了私有成员的方法,那么私有成员对外部就是不可见的,它里面的方法就不会和外面的方法混杂起来

    package cn.xf.cp.ch02.item16;
    
    import java.util.Collection;
    import java.util.Set;
    
    /**
     * 
     *功能:包装类
     *时间:下午9:58:36
     *文件:InstrumentedSet.java 
     *@author xiaof 
     *
     * @param <E>
     */
    public class InstrumentedSet<E> extends ForwardingSet<E>
    {
        private int addCount = 0;    //用来统计set添加了多少元素
    
        public InstrumentedSet(Set<E> s)
        {
            super(s);
        }
        
        @Override
        public boolean add(E e)
        {
            ++addCount;
            return super.add(e);
        }
        
        @Override
        public boolean addAll(Collection<? extends E> c)
        {
            addCount += c.size();
            return super.addAll(c);
        }
        
        public int getAddCount()
        {
            return addCount;
        }
    
    }
  • 相关阅读:
    不错的电影(先收藏着)
    getchar() getch() getche() gets() puts() scanf()的用法及区别
    java反射获取字段的属性值,以及为字段赋值等方法
    oracle将查询结果横转纵
    关于MySQL 的LEFT JOIN ON的问题
    MySQL表名和数据库关键字相同解决办法
    ajax 后台正常执行 错误类型却是404
    BIT 树状数组 详解 及 例题
    HDU 2689 Sort it (树状数组)
    HDU Cow Sorting (树状数组)
  • 原文地址:https://www.cnblogs.com/cutter-point/p/5866587.html
Copyright © 2011-2022 走看看