天天看點

深入學習java源碼之AbstractCollection.contains()與AbstractCollection.toArray()

深入學習java源碼之AbstractCollection.contains()與AbstractCollection.toArray()

Iterable接口與Iterator接口

Iterator接口

  疊代器是一種設計模式,它是一個對象,它可以周遊并選擇序列中的對象,而開發人員不需要了解該序列的底層結構。疊代器通常被稱為“輕量級”對象,因為建立它的代價小。

  Java中的Iterator功能比較簡單,并且隻能單向移動:

使用方法iterator()要求容器傳回一個Iterator。第一次調用Iterator的next()方法時,它傳回序列的第一個元素。注意:iterator()方法是java.lang.Iterable接口,被Collection繼承。

實作周遊ArrayList<String>類型。

一開始疊代器在所有元素的左邊,調用next()之後,疊代器移到第一個和第二個元素之間,next()方法傳回疊代器剛剛經過的元素。

hasNext()若傳回True,則表明接下來還有元素,疊代器不在尾部。

remove()方法必須和next方法一起使用,功能是去除剛剛next方法傳回的元素。

  Iterator是Java疊代器最簡單的實作,為List設計的ListIterator具有更多的功能,它可以從兩個方向周遊List,也可以從List中插入和删除元素。

import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;

public class ForEachDemo {
    public static void main(String... arg) {
        Collection<String> a = new ArrayList<String>();
        a.add("Bob");
        a.add("Alice");
        a.add("Lisy");

        Iterator<String> iterator = a.iterator();
        while (iterator.hasNext()) {
            String ele = iterator.next();
            System.out.println(ele);//Bob  Alice  Lisy    
        }
        System.out.println(a);//[Bob, Alice, Lisy]  
        iterator = a.iterator();
        iterator.next();
        iterator.remove();
        System.out.println(a);//[Alice, Lisy]  
    }
}  
           
list l = new ArrayList();
 l.add("aa");
 l.add("bb");
 l.add("cc");
 for (Iterator iter = l.iterator(); iter.hasNext();) {
     String str = (String)iter.next();
     System.out.println(str);
 }
 /*疊代器用于while循環
 Iterator iter = l.iterator();
 while(iter.hasNext()){
     String str = (String) iter.next();
     System.out.println(str);
 }
 */
           

Iterable接口

for-each循環可以與任何實作了Iterable接口的對象一起工作。

而java.util.Collection接口繼承java.lang.Iterable,故标準類庫中的任何集合都可以使用for-each循環。

為什麼一定要去實作Iterable這個接口呢? 為什麼不直接實作Iterator接口呢?

看一下JDK中的集合類,比如List一族或者Set一族,

都是繼承了Iterable接口,但并不直接繼承Iterator接口。

仔細想一下這麼做是有道理的。因為Iterator接口的核心方法next()或者hasNext()

是依賴于疊代器的目前疊代位置的。

如果Collection直接繼承Iterator接口,勢必導緻集合對象中包含目前疊代位置的資料(指針)。

當集合在不同方法間被傳遞時,由于目前疊代位置不可預置,那麼next()方法的結果會變成不可預知。

除非再為Iterator接口添加一個reset()方法,用來重置目前疊代位置。

但即時這樣,Collection也隻能同時存在一個目前疊代位置。

而Iterable則不然,每次調用都會傳回一個從頭開始計數的疊代器。

多個疊代器是互不幹擾的。

class Student {
    private String sid;
    private String name;

    public Student(String sid, String name) {
        setSid(sid);
        setName(name);
    }

    public String getSid() {
        return sid;
    }

    public void setSid(String sid) {
        this.sid = sid;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Student{" +
                "sid='" + sid + '\'' +
                ", name='" + name + '\'' +
                '}';
    }
}
           

支援for each疊代循環的學生集合類

class Students implements Iterable<Student> {
    // 存儲所有學生類的數組
    private Student[] students;

    // 該構造函數可以生成指定大小的學生類變量數組,并初始化該學生類變量數組
    public Students(int size) {
        students = new Student[size];
        for (int i = 0; i < size; i++) {
            students[i] = new Student(String.valueOf(i), "學生" + String.valueOf(i));
        }
    }

    @Override
    public Iterator<Student> iterator() {
        return new StudentIterator();
    }

    // 實作Iterator接口的私有内部類,外界無法直接通路
    private class StudentIterator implements Iterator<Student> {
        // 目前疊代元素的下标
        private int index = 0;

        // 判斷是否還有下一個元素,如果疊代到最後一個元素就傳回false
        public boolean hasNext() {
            return index != students.length;
        }

        @Override
        public Student next() {
            return students[index++];
        }

        // 這裡不支援,抛出不支援操作異常
        public void remove() {
            throw new UnsupportedOperationException();
        }
    }
}
           
public class ForEachAPIDemo {
    public static void main(String[] args) throws Exception {
        Students students = new Students(10);
        for (Student student : students) {
            System.out.println(student.getSid() + ":" + student.getName());
        }
    }
}
           

AbstractCollection實作自己的可疊代集合類

Colllection是  java.uitl包中所有集合類的一個根接口..  是以我們可以通過實作Collection接口來實作自己的集合類..

不過由于Collection接口 方法太多.. 于是JDK提供了AbstractCollection抽象類...

這個類是Collection的一個骨幹..即為我們提供了Collection的大量實作..我們隻需要實作  iterator 和size方法 ...如果我們想要修改自己建立的容器那麼要實作add和remove方法否則 。。

進行修改操作會抛出UnSupporttedException異常   下面是一個例子 ...

在生成疊代器的時候結合局部内部類使用

class Info{
 String info=null ;
 public Info(String name) {
     this.info=name ;
 }
 @Override
 public String toString() {
  return this.getClass().getName()+": "+info;
 }
}  
           
import java.util.AbstractCollection;
import java.util.Iterator;



class  MyCollection extends  AbstractCollection<Info>{  
 private Info []arr =new Info[100]; 
 private int count= 0;  
 public  boolean add(Info info){
  if(count<=arr.length){
      arr[count++]=info ;
   return true ;
  }
  return false; 
 }
@Override
 public boolean equals(Object obj) {
  // TODO Auto-generated method stub
  return super.equals(obj);
 }
 @Override
 public Iterator<Info> iterator() {

  return new Iterator<Info>() {
            
   private int flag=0 ;
   @Override
   public boolean hasNext() {
    
    return flag<MyCollection.this.count ;
   }
   @Override
   public Info next() {
    
    return arr[flag++];
   }
   @Override
   public void remove() {   //支援删除操作
          throw new  UnsupportedOperationException() ;      
   }
  };
 }
 @Override
 public int size() {
  return 0;
 }
}  
           
public class Me   {   
 public static void main(String []agrs){  
  MyCollection me=new MyCollection() ;
  me.add(new Info("zhangsan ")) ;
  me.add(new Info("lisi ")) ;
  me.add(new Info("zwangwu ")) ;
  me.add(new Info("zmaliu ")) ; 
  for(Info i:me){
   System.out.println(i);
  }

 }
}
           

java源碼

Modifier and Type Method and Description

boolean

add(E e)

確定此集合包含指定的元素(可選操作)。

boolean

addAll(Collection<? extends E> c)

将指定集合中的所有元素添加到此集合(可選操作)。

void

clear()

從此集合中删除所有元素(可選操作)。

boolean

contains(Object o)

如果此集合包含指定的元素,則傳回 true 。

boolean

containsAll(Collection<?> c)

如果此集合包含指定 集合中的所有元素,則傳回true。

boolean

isEmpty()

如果此集合不包含元素,則傳回 true 。

abstract Iterator<E>

iterator()

傳回包含在該集合中的元素的疊代器。

boolean

remove(Object o)

從該集合中删除指定元素的單個執行個體(如果存在)(可選操作)。

boolean

removeAll(Collection<?> c)

删除指定集合中包含的所有此集合的元素(可選操作)。

boolean

retainAll(Collection<?> c)

僅保留此集合中包含在指定集合中的元素(可選操作)。

abstract int

size()

傳回此集合中的元素數。

Object[]

toArray()

傳回一個包含此集合中所有元素的數組。

<T> T[]

toArray(T[] a)

傳回包含此集合中所有元素的數組; 傳回的數組的運作時類型是指定數組的運作時類型。

String

toString()

傳回此集合的字元串表示形式。
package java.util;

public abstract class AbstractCollection<E> implements Collection<E> {

    protected AbstractCollection() {
    }

    public abstract Iterator<E> iterator();

    public abstract int size();

    public boolean isEmpty() {
        return size() == 0;
    }

    public boolean contains(Object o) {
        Iterator<E> it = iterator();
        if (o==null) {
            while (it.hasNext())
                if (it.next()==null)
                    return true;
        } else {
            while (it.hasNext())
                if (o.equals(it.next()))
                    return true;
        }
        return false;
    }

    public Object[] toArray() {
        // Estimate size of array; be prepared to see more or fewer elements
        Object[] r = new Object[size()];
        Iterator<E> it = iterator();
        for (int i = 0; i < r.length; i++) {
            if (! it.hasNext()) // fewer elements than expected
                return Arrays.copyOf(r, i);
            r[i] = it.next();
        }
        return it.hasNext() ? finishToArray(r, it) : r;
    }
	
    @SuppressWarnings("unchecked")
    public <T> T[] toArray(T[] a) {
        // Estimate size of array; be prepared to see more or fewer elements
        int size = size();
        T[] r = a.length >= size ? a :
                  (T[])java.lang.reflect.Array
                  .newInstance(a.getClass().getComponentType(), size);
        Iterator<E> it = iterator();

        for (int i = 0; i < r.length; i++) {
            if (! it.hasNext()) { // fewer elements than expected
                if (a == r) {
                    r[i] = null; // null-terminate
                } else if (a.length < i) {
                    return Arrays.copyOf(r, i);
                } else {
                    System.arraycopy(r, 0, a, 0, i);
                    if (a.length > i) {
                        a[i] = null;
                    }
                }
                return a;
            }
            r[i] = (T)it.next();
        }
        // more elements than expected
        return it.hasNext() ? finishToArray(r, it) : r;
    }	
	
    private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;	
	
    @SuppressWarnings("unchecked")
    private static <T> T[] finishToArray(T[] r, Iterator<?> it) {
        int i = r.length;
        while (it.hasNext()) {
            int cap = r.length;
            if (i == cap) {
                int newCap = cap + (cap >> 1) + 1;
                // overflow-conscious code
                if (newCap - MAX_ARRAY_SIZE > 0)
                    newCap = hugeCapacity(cap + 1);
                r = Arrays.copyOf(r, newCap);
            }
            r[i++] = (T)it.next();
        }
        // trim if overallocated
        return (i == r.length) ? r : Arrays.copyOf(r, i);
    }

    private static int hugeCapacity(int minCapacity) {
        if (minCapacity < 0) // overflow
            throw new OutOfMemoryError
                ("Required array size too large");
        return (minCapacity > MAX_ARRAY_SIZE) ?
            Integer.MAX_VALUE :
            MAX_ARRAY_SIZE;
    }	
	
    public boolean add(E e) {
        throw new UnsupportedOperationException();
    }	
	
    public boolean remove(Object o) {
        Iterator<E> it = iterator();
        if (o==null) {
            while (it.hasNext()) {
                if (it.next()==null) {
                    it.remove();
                    return true;
                }
            }
        } else {
            while (it.hasNext()) {
                if (o.equals(it.next())) {
                    it.remove();
                    return true;
                }
            }
        }
        return false;
    }	
	
    public boolean containsAll(Collection<?> c) {
        for (Object e : c)
            if (!contains(e))
                return false;
        return true;
    }	
	
    public boolean addAll(Collection<? extends E> c) {
        boolean modified = false;
        for (E e : c)
            if (add(e))
                modified = true;
        return modified;
    }	
	
    public boolean removeAll(Collection<?> c) {
        Objects.requireNonNull(c);
        boolean modified = false;
        Iterator<?> it = iterator();
        while (it.hasNext()) {
            if (c.contains(it.next())) {
                it.remove();
                modified = true;
            }
        }
        return modified;
    }	
	
    public boolean retainAll(Collection<?> c) {
        Objects.requireNonNull(c);
        boolean modified = false;
        Iterator<E> it = iterator();
        while (it.hasNext()) {
            if (!c.contains(it.next())) {
                it.remove();
                modified = true;
            }
        }
        return modified;
    }
	
    public void clear() {
        Iterator<E> it = iterator();
        while (it.hasNext()) {
            it.next();
            it.remove();
        }
    }	
	
    public String toString() {
        Iterator<E> it = iterator();
        if (! it.hasNext())
            return "[]";

        StringBuilder sb = new StringBuilder();
        sb.append('[');
        for (;;) {
            E e = it.next();
            sb.append(e == this ? "(this Collection)" : e);
            if (! it.hasNext())
                return sb.append(']').toString();
            sb.append(',').append(' ');
        }
    }

}	
           
Modifier and Type Method and Description

boolean

add(E e)

確定此集合包含指定的元素(可選操作)。

boolean

addAll(Collection<? extends E> c)

将指定集合中的所有元素添加到此集合(可選操作)。

void

clear()

從此集合中删除所有元素(可選操作)。

boolean

contains(Object o)

如果此集合包含指定的元素,則傳回 true 。

boolean

containsAll(Collection<?> c)

如果此集合包含指定 集合中的所有元素,則傳回true。

boolean

equals(Object o)

将指定的對象與此集合進行比較以獲得相等性。

int

hashCode()

傳回此集合的哈希碼值。

boolean

isEmpty()

如果此集合不包含元素,則傳回 true 。

Iterator<E>

iterator()

傳回此集合中的元素的疊代器。

default Stream<E>

parallelStream()

傳回可能并行的

Stream

與此集合作為其來源。

boolean

remove(Object o)

從該集合中删除指定元素的單個執行個體(如果存在)(可選操作)。

boolean

removeAll(Collection<?> c)

删除指定集合中包含的所有此集合的元素(可選操作)。

default boolean

removeIf(Predicate<? super E> filter)

删除滿足給定謂詞的此集合的所有元素。

boolean

retainAll(Collection<?> c)

僅保留此集合中包含在指定集合中的元素(可選操作)。

int

size()

傳回此集合中的元素數。

default Spliterator<E>

spliterator()

建立一個

Spliterator

在這個集合中的元素。

default Stream<E>

stream()

傳回以此集合作為源的順序

Stream

Object[]

toArray()

傳回一個包含此集合中所有元素的數組。

<T> T[]

toArray(T[] a)

傳回包含此集合中所有元素的數組; 傳回的數組的運作時類型是指定數組的運作時類型。
package java.util;

import java.util.function.Predicate;
import java.util.stream.Stream;
import java.util.stream.StreamSupport;

public interface Collection<E> extends Iterable<E> {

    int size();
	
    boolean isEmpty();	
	
    boolean contains(Object o);	
	
    Iterator<E> iterator();	
	
    Object[] toArray();	
	
    <T> T[] toArray(T[] a);	
	
    boolean add(E e);	
	
    boolean remove(Object o);	
	
    boolean containsAll(Collection<?> c);
	
    boolean addAll(Collection<? extends E> c);	
	
    boolean removeAll(Collection<?> c);	
	
    default boolean removeIf(Predicate<? super E> filter) {
        Objects.requireNonNull(filter);
        boolean removed = false;
        final Iterator<E> each = iterator();
        while (each.hasNext()) {
            if (filter.test(each.next())) {
                each.remove();
                removed = true;
            }
        }
        return removed;
    }	
	
    boolean retainAll(Collection<?> c);	
	
    void clear();	
	
    boolean equals(Object o);	
	
    int hashCode();	
	
    @Override
    default Spliterator<E> spliterator() {
        return Spliterators.spliterator(this, 0);
    }	
	
    default Stream<E> stream() {
        return StreamSupport.stream(spliterator(), false);
    }	
	
    default Stream<E> parallelStream() {
        return StreamSupport.stream(spliterator(), true);
    }
}
           

實作此接口允許對象成為“for-each loop”語句的目标。

Modifier and Type Method and Description

default void

forEach(Consumer<? super T> action)

Iterable

的每個元素執行給定的操作,直到所有元素都被處理或動作引發異常。

Iterator<T>

iterator()

傳回類型為

T

元素的疊代器。

default Spliterator<T>

spliterator()

在Iterable描述的元素上建立一個

Iterable

package java.lang;

import java.util.Iterator;
import java.util.Objects;
import java.util.Spliterator;
import java.util.Spliterators;
import java.util.function.Consumer;

public interface Iterable<T> {

    Iterator<T> iterator();

    default void forEach(Consumer<? super T> action) {
        Objects.requireNonNull(action);
        for (T t : this) {
            action.accept(t);
        }
    }

    default Spliterator<T> spliterator() {
        return Spliterators.spliteratorUnknownSize(iterator(), 0);
    }
}
           
Modifier and Type Method and Description

default void

forEachRemaining(Consumer<? super E> action)

對每個剩餘元素執行給定的操作,直到所有元素都被處理或動作引發異常。

boolean

hasNext()

如果疊代具有更多元素,則傳回

true

E

next()

傳回疊代中的下一個元素。

default void

remove()

從底層集合中删除此疊代器傳回的最後一個元素(可選操作)。
package java.util;

import java.util.function.Consumer;

public interface Iterator<E> {

    boolean hasNext();

    E next();

    default void remove() {
        throw new UnsupportedOperationException("remove");
    }

    default void forEachRemaining(Consumer<? super E> action) {
        Objects.requireNonNull(action);
        while (hasNext())
            action.accept(next());
    }
}
           

繼續閱讀