Java 集合

集合主要技术

  • 了解Collection和Map
  • Collection接口
  • ArrayList类
  • HashSet类
  • HashMap类
  • Collections工具类
  • 泛型

一 .Collection和Map

Collection集合继承关系图
Map集合继承关系图

线程安全:多线程访问时,采用了加锁机制,当一个线程访问该类的某个数据时,进行保护,其他线程不能进行访问直到该线程读取完,其他线程才可使用。不会出现数据不一致或者数据污染。

Collection

  • Collection是对象集合,有两个子接口 List 和 Set,ArrayList、Vector 、LinkedList是List的实现类

  • ArrayList 是线程不安全的, Vector 是线程安全的,这两个类底层都是由数组实现的。

  • LinkedList是线程不安全的,底层是由链表实现的。

  • ArrayList和LinkedList的操作基本一致;HashSet和LinkedHashSet的操作基本一致。

Map是键值对集合

  • HashTable和HashMap是 Map 的实现类。

  • HashTable是线程安全的,不能存储 null 值;HashMap 不是线程安全的,可以存储 null 值。

  • HashTable的子类Properties类表示了一个持久的属性集,用于小型数据的持久化保存。

二.Collection接口

  • 1.创建:由于接口不能用来实例化一个对象,所以我们实例化其子类,利用多态性接受来测试Collection接口的方法。创建的时候需要明确存放的内容是什么类型。
Collection<String> collection = new ArrayList();
  • 2.添加:直接在末尾添加指定对象或者添加某个集合的内容
//末尾添加
boolean add(E e);

collection.add("Jack");
collection.add("Mary");
System.out.println(collection);

输出:[Jack, Mary]

//添加一个集合
boolean addAll(Collection<? extends E> c);

collection.clear();//清空
Collection<String> collectionTemp = new ArrayList();
collectionTemp.add("Jack");
collectionTemp.add("Mary");

collection.addAll(collectionTemp);
System.out.println(collection);

输出:[Jack, Mary]
  • 3.移除:移除指定对象,移除指定集合内对象,除了指定集合内的元素外其余元素全部移除,按照指定条件移除
//移除指定对象
boolean remove(Object obj);

collection.remove("Jack");
System.out.println(collection);

输出:[Mary]

//移除指定集合对象
boolean removeAll(Collection<?> c);

Collection<Integer> collectionTemp1 = new ArrayList();
collectionTemp1.add(1);
collectionTemp1.add(2);
collectionTemp1.add(3);
Collection<Integer> temp = new ArrayList();
temp.add(1);
collectionTemp1.removeAll(temp);
System.out.println(collectionTemp1);

输出:[2, 3]

//除了指定集合内的元素外其余元素全部移除
boolean retainAll(Collection<?> c);

Collection<Integer> collectionTemp1 = new ArrayList();
collectionTemp1.add(1);
collectionTemp1.add(2);
collectionTemp1.add(3);
Collection<Integer> temp = new ArrayList();
temp.add(1);
collectionTemp1.retainAll(temp);
System.out.println(collectionTemp1);

输出:[1]

//按照指定条件移除
boolean removeIf(Predicate<? super E> p)

Collection<Integer> collectionTemp1 = new ArrayList();
collectionTemp1.add(1);
collectionTemp1.add(2);
collectionTemp1.add(3);
collectionTemp1.removeIf(obj -> obj > 2);
System.out.println(collectionTemp1);

输出:[1, 2]
  • 4.获取元素个数
int size();

System.out.println(collection.size());

输出:1
  • 5.判断一个元素是否包含另一个元素
boolean contains(Object obj);

if (collection.contains("Mary")) {
     System.out.println("有Mary");
}else {
     System.out.println("有Mary");
}

输出:有Mary
  • 6.判断是否为空
boolean isEmpty();

//判断是否为空
if (collection.isEmpty()){
   System.out.println("是空的");
}else{
   System.out.println("不是空的");
}

输出:不是空的
  • 7.判断两个集合是否相同
boolean equals(Object obj);

if (collection.equals(collectionTemp)){
    System.out.println("相同");
}else{
   System.out.println("不相同");
}
  • 8.转化成不可变的普通数组
//转化成为Object类型的不可变数组
Object[] toArray();

Object[] array1 = collectionTemp.toArray();
for (Object obj : array1) {
    System.out.print((String)obj);
}

输出:JackMary

//转化成为指定类型的不可变数组
<T> T[] toArray(T[] t);

Integer[] array2 = new Integer[collectionTemp.size()];
array2 = collectionTemp.toArray(array2);
for (String str : array2) {
    System.out.print(str);
}

输出:JackMary
  • 9.迭代器遍历:迭代器刚开始不指向第一个位置,下一个才是第一个位置
//获得当前集合的迭代器
Iterator<E> iterator();

//判断下一个位置是否有元素
boolean hasNext();

//指向下一个位置,并返回下一个位置的值
E next();

Iterator iterator = collectionTemp.iterator();
while (iterator.hasNext()){
    System.out.print(iterator.next());
}

//输出:JackMary
  • 10.清空集合
void clear();

collection.clear();
System.out.println(collection);

输出:[]

三.ArrayList

ArrayList实现了Collection接口,Collection有的方法ArrayList都有,并且在其基础上还有更多的方法。接下里说一下ArrayList比Collection多的方法。

1.创建

ArrayList<Integer> score = new ArrayList();

2.添加

  • Collection接口提供的方法
//添加指定对象
boolean add(E e);

//添加一个集合
boolean addAll(Collection<? extends E> c);
  • 新的方法:在指定索引位置添加对象
public void add(int offset, E e);
score.add(2);//末尾添加
score.add(0,3);//指定位置插入
System.out.println(score);

输出:[3, 2]

3.访问指定索引位置的元素

public E get(int offset);
System.out.println(score.get(0));

输出:3

4.修改指定索引位置元素

public E set(int offset, E e);
score.set(0,1);
System.out.println(score);

输出:[1, 2]

5.返回给定对象的索引值

//返回指定对象第一次出现的索引位置
public int indexOf(Object obj)

//返回指定对象最后一次出现的索引位置
public int lastIndexOf(Object obj)

6.返回给定集合某一块的子集合

public List<E> subList(int offset, int len)
System.out.println(score.subList(0,1));

输出:[1]

7.移除

  • Collection接口提供的方法
//移除指定对象
boolean remove(Object obj);

//移除指定集合对象
boolean removeAll(Collection<?> c);

//除了指定集合内的元素外其余元素全部移除
boolean retainAll(Collection<?> c);

//按照指定条件移除
boolean removeIf(Predicate<? super E> p)
  • 新的方法:移除指定索引位置对象
public E remove(int offset)
  • 混淆问题:操作是对象,为什么我们可以对基本类型进行操作呢。因为Java内部有装盒(例如:int->Integer)和拆盒(例如:Integer->int)的操作。
//删除指定位置的元素
score.remove(0);
System.out.println(score);
输出:[2]

//删除指定对象
score.remove((Integer) 2);
System.out.println(score);
输出:[]

8.排序

public void sort(Comparator<? super E> c)
  • 排序重点是创建一个比较器对象,首先说系统提供好的升序和降序比较器。
ArrayList<Integer> list = new ArrayList();
list.add(1);
list.add(2);
list.add(3);
list.add(4);
list.add(5);
list.add(6);

//降序
list.sort(Comparator.reverseOrder());
System.out.println(list);

//升序
list.sort(Comparator.naturalOrder());
System.out.println(list);

输出:
[6, 5, 4, 3, 2, 1]
[1, 2, 3, 4, 5, 6]
  • 根据想要比较的对象创建
list.sort(Comparator.reverseOrder());
System.out.println(list);

//升序
list.sort(Comparator.comparing(Integer::intValue));
System.out.println(list);

输出:
[6, 5, 4, 3, 2, 1]
[1, 2, 3, 4, 5, 6]
  • 自己创建一个类实现Comparator接口
class XLCompare implements Comparator{

    @Override
    public int compare(Object o1, Object o2) {
        int mo1 = (int)o1;
        int mo2 = (int)o2;

        return mo1 - mo2;
    }
}

list.sort(Comparator.reverseOrder());
System.out.println(list);

list.sort(new XLCompare());
System.out.println(list);

输出:
[6, 5, 4, 3, 2, 1]
[1, 2, 3, 4, 5, 6]
  • 使用匿名类完成:什么时候需要自己手动创建比较器,如果系统默认提供的方法不能完成我们的比较
list.sort(Comparator.reverseOrder());
System.out.println(list);

list.sort(new Comparator<Integer>() {
    @Override
    public int compare(Integer integer, Integer t1) {
        return integer-t1;
    }
});
System.out.println(list);

输出:
[6, 5, 4, 3, 2, 1]
[1, 2, 3, 4, 5, 6]
  • 使用Lambda 表达式
list.sort(Comparator.reverseOrder());
System.out.println(list);

list.sort((Integer i1,Integer i2)->i1-i2);
System.out.println(list);
  • 例子:比较两个自定义的对象
public class Person {
    String name;
    int age;

    public Person(String name,int age){
        this.name = name;
        this.age = age;
    }
}

class XLCompare implements Comparator{

    @Override
    public int compare(Object o1, Object o2) {
        Public p1 = (Public)o1;
        Public p2 = (Public)o2;
        
        if(p1.age != p2.age){
             return p1.age - p2.age;
        }else{
             return p1.name - p2.name;
        }
    }
}

ArrayList<Person> list = new ArrayList();

String[] names = {"张明","张杰","李明浩","李浩天","李隆基","李世明"};

for (int i = 0; i < names.length; i++) {
    Person person = new Person(names[i],i+30);
    list.add(person);
}

list.sort(new XLCompare());

四.HashSet

1.简述

  • Set里面元素不能重复,如果重复添加不进去;其内部使用HashMap来实现,键值对中键key不能重复。内部是通过计算每个key的hash值,是在对象的地址的基础上得到的值;Object类有一个方法public native int hashCode();用来返回hash值;切记重写类的equals方法一定要重写hashCode方法,hashCode和equals详解。Object类还有一个方法protected native Object clone() throws CloneNotSupportedException;用于复制对象,clone详解

  • Set是无序的,添加的顺序和存储的顺序无关;而ArrayList添加的顺序和存储的顺序有关。

  • Hash大部分的操作可以参照Collection接口。

  • HashSet内部的顺序是按照默认的顺序排列的;TreeSet则可以使用我们给定的顺序排列。

2.HashSet代码例子

HashSet<String> hashSet = new HashSet<>();

hashSet.add("java");
hashSet.add("java");
hashSet.add("jack");
hashSet.add("Android");
System.out.println(hashSet);
//[java, jack, Android]

hashSet.removeIf(element->element.compareTo("c") > 0);
System.out.println(hashSet);
//[Android]

3.TreeSet代码例子

  • 可以在TreeSet的构造方法中传入一个比较器Comparator,这又涉及到Comparator和Comparable两个接口的区别

  • Comparator 则是在外部制定排序规则,然后作为排序策略参数传递给某些类,例如ArrayList的sort方法,TreeSet的构造方法。

  • 自然排序需要类实现 Comparable,并且在内部重写 comparaTo 方法。Object类有一个用于比较的方法public boolean equals(Object var1) {return this == var1;},就需要类实现 Comparable。系统内部的类基本上都实现了Comparable接口,如果我们自定义的类需要比较,那么一定要实现 Comparable接口。

class Person implements Comparable{
    String name;
    int age;

    public Person(String name,int age){
        this.name = name;
        this.age = age;
    }

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

    //equals比较的是对象内部的内容
    //所有的对象要能参加比较,必须实现Comparable
    //接口compareTo方法
    //在compareTo中做具体的比较
    @Override
    public int compareTo(Object o) {
        //判断o对象是不是Person的一个对象
        if (o instanceof Person){
            //自己规定返回的策略
            if (this.age != ((Person) o).age){
                return this.age-((Person) o).age;
            }else {
                //年龄相同的情况下再比姓名
                return this.name.compareTo(((Person) o).name);
            }
        }else {
            return -1;
        }
    }
}
TreeSet<Integer> score = new TreeSet<>();

score.add(32);
score.add(45);
score.add(12);
System.out.println(score);
//[12, 32, 45]

//Lambda表达式方式
TreeSet<Person> persons = new TreeSet<>((Person p1,Person p2)->p1.compareTo(p2));

//匿名类方式
/*TreeSet<Person> persons = new TreeSet<>(new Comparator<Person>() {
    @Override
    public int compare(Person person, Person t1) {
        return person.compareTo(t1);
    }
});*/

Person p1 = new Person("仙王",18);
Person p2 = new Person("武帝",18);
Person p3 = new Person("开天",18);

persons.add(p1);
persons.add(p2);
persons.add(p3);

System.out.println(persons);

输出:[Person{name='仙王', age=18}, Person{name='开天', age=18}, Person{name='武帝', age=18}]

五.HashMap

一.概述

  • HashMap集合存储数据的特点:键key-值value

  • key不能重复,可以是任意的对象类型,通常使用字符串

二.方法

  • 1.创建对象:需要制定键和值得类型。
HashMap<String,Integer> score = new HashMap<>();
  • 2.添加键值对:添加的键值相同的情况,后面的默认更改值。
public V put(K key, V value)

添加一个HashMap

public void putAll(Map<? extends K, ? extends V> m)
//添加对象:键值对
score.put("Chinese",90);
score.put("English",88);
score.put("Math",100);

//相同的情况,默认更改其值
score.put("Chinese",95);
System.out.println(score);

输出:{English=88, Chinese=95, Math=100}
  • 3.获取键值对的个数
public int size()
System.out.println(score.size());

输出:3
  • 4.获取所有的key
public Set<K> keySet()
System.out.println(score.keySet());

输出:[English, Chinese, Math]
  • 5.获取所有的value
public Collection<V> values()
System.out.println(score.values());

输出:[88, 95, 100]
  • 6.获取一个键对应的值,如果key不存在,返回null
public V get(Object obj)
System.out.println(score.get("Chinese"));

输出:95
  • 7.返回包含映射的Set视图。
public Set<Entry<K, V>> entrySet()
System.out.println(score.entrySet());

输出:[English=88, Chinese=95, Math=100]
  • 8.键值对的遍历
//1.通过遍历key得到每一个key对应的值
for (String key : score.keySet()) {
    //通过key得到值
    int value  = score.get(key);
    System.out.println("key:"+key+" "+"value;"+value);
}

输出:
key:English value;88
key:Chinese value;95
key:Math value;100
//2.通过entrySet 得到Entry对象的集合
//一个entry管理一个键值对 getKey getValue
Set<Map.Entry<String ,Integer>> entrys = score.entrySet();
for (Map.Entry entry : entrys) {
    //得到entry对应的key
    String key = (String)entry.getKey();
    //得到entry对应的value
    Integer value = (Integer)entry.getValue();
    System.out.println("key:"+key+" "+"value;"+value);
}

输出:
key:English value;88
key:Chinese value;95
key:Math value;100
  • 9.删除制定键对应的映射关系
public V remove(Object obj)
score.remove("Chinese");
System.out.println(score);

输出:{English=88, Math=100}
  • 10.替换指定键对应的值
public V replace(K key, V value)
score.replace("English",90);
System.out.println(score);

输出:{English=90, Math=100}
  • 11.判断是否为空
public boolean isEmpty()
  • 12.清空所有映射关系
public void clear();

六.Collections工具类

  • 1.获取List中的最小值
List<Integer> intList = Arrays.asList(33, 24, 18, 6, 9, 99);  
// 6  
System.out.println(java.util.Collections.min(intList));  
  • 2.获取List中的最大值
List<Integer> intList = Arrays.asList(33, 24, 18, 6, 9, 99);  
// 99  
System.out.println(java.util.Collections.max(intList));  
  • 3.Shuffle方法可以使一个集合的元素乱序化。
List<Integer> intList = Arrays.asList(33, 24, 18, 6, 9, 99);  
Collections.shuffle(intList);  
// 一次测试的结果  
// [6, 18, 33, 24, 99, 9]  
System.out.println(intList); 
  • 4. nCopies返回一个不可变列表组成的n个拷贝的指定对象。
// 生成一个由10个100组成的整数列表  
List<Integer> nCopiesList = Collections.nCopies(10, 100);  
//[100, 100, 100, 100, 100, 100, 100, 100, 100, 100]  
System.out.println(nCopiesList);  
  • 5.sort用于对集合排序。
List<Integer> intList = Arrays.asList(33, 24, 18, 6, 9, 99);  
Collections.sort(intList);  
  • 6.binarySearch用于查找给定元素在给定数组的索引值。
List<Integer> intList = Arrays.asList(33, 24, 18, 6, 9, 99);  
// 2  
System.out.println(Collections.binarySearch(intList, 18));  
  • 7.frequency获取某个元素在集合出现的次数。
List<String> testList = Arrays.asList("A", "B", "C", "D");  
int freq = Collections.frequency(testList, "A");  
// 1  
System.out.println(freq); 
  • 8.indexOfSubList返回指定源列表中第一次出现指定目标列表的起始位置。
int index = Collections.indexOfSubList(Arrays.asList("A", "B", "C"),  
Arrays.asList("B"));  
// Print 1  
System.out.println(index);  
  • 9.lastIndexOfSubList返回指定源列表中最后一次出现指定目标列表的起始位置。
int lastIndex = Collections.lastIndexOfSubList(  
        Arrays.asList("A", "B", "C", "B"), Arrays.asList("B"));  
// Print 3  
System.out.println(lastIndex);  
  • 10.reverse反转列表中的元素顺序。
List<String> reverseCandidate = Arrays.asList("A", "B", "C");  
Collections.reverse(reverseCandidate);  
// [C, B, A]  
System.out.println(reverseCandidate);  

七.泛型

1.泛型方法

  • 泛型方法,该方法在调用时可以接收不同类型的参数。根据传递给泛型方法的参数类型,编译器适当地处理每一个方法调用。

  • 所有泛型方法声明都有一个类型参数声明部分(由尖括号分隔),该类型参数声明部分在方法返回类型之前(在下面例子中的<E>)。

  • 每一个类型参数声明部分包含一个或多个类型参数,参数间用逗号隔开。一个泛型参数,也被称为一个类型变量,是用于指定一个泛型类型名称的标识符。

  • 类型参数能被用来声明返回值类型,并且能作为泛型方法得到的实际参数类型的占位符。

  • 泛型方法体的声明和其他方法一样。注意类型参数只能代表引用型类型,不能是原始类型(像int,double,char的等)。

public class GenericMethodTest{
   // 泛型方法 printArray                         
   public static < E > void printArray( E[] inputArray ){
      // 输出数组元素            
         for ( E element : inputArray ){        
            System.out.printf( "%s ", element );
         }
         System.out.println();
    }
 
    public static void main( String args[] ){
        // 创建不同类型数组: Integer, Double 和 Character
        Integer[] intArray = { 1, 2, 3, 4, 5 };
        Double[] doubleArray = { 1.1, 2.2, 3.3, 4.4 };
        Character[] charArray = { 'H', 'E', 'L', 'L', 'O' };
 
        System.out.println( "整型数组元素为:" );
        printArray( intArray  ); // 传递一个整型数组
 
        System.out.println( "\n双精度型数组元素为:" );
        printArray( doubleArray ); // 传递一个双精度型数组
 
        System.out.println( "\n字符型数组元素为:" );
        printArray( charArray ); // 传递一个字符型数组
    } 
}

输出:
整型数组元素为:
1 2 3 4 5 

双精度型数组元素为:
1.1 2.2 3.3 4.4 

字符型数组元素为:
H E L L O 

2.泛型类

  • 泛型类的声明和非泛型类的声明类似,除了在类名后面添加了类型参数声明部分。

  • 和泛型方法一样,泛型类的类型参数声明部分也包含一个或多个类型参数,参数间用逗号隔开。

  • 一个泛型参数,也被称为一个类型变量,是用于指定一个泛型类型名称的标识符。

public class MyClass {

    public static void main(String[] args){
        //创建类,明确指定T指定的类型
        GenericTest<String> genericTest = new GenericTest<>();

        genericTest.test("java","oc");

        System.out.println(genericTest.a1);
    }
}

class GenericTest<T>{
    int age;
    T a1;
    T a2;

    public void test(T a1,T a2){
        this.a1 = a1;
        this.a2 = a2;

        System.out.println(a1.equals(a2));
    }
}

3.类型通配符

类型通配符一般是使用?代替具体的类型参数。例如 List<?> 在逻辑上是List<String>,List<Integer> 等所有List<具体类型实参>的父类。

import java.util.*;
 
public class GenericTest {
     
    public static void main(String[] args) {
        List<String> name = new ArrayList<String>();
        List<Integer> age = new ArrayList<Integer>();
        List<Number> number = new ArrayList<Number>();
        
        name.add("icon");
        age.add(18);
        number.add(314);
 
        getData(name);
        getData(age);
        getData(number);
       
   }
 
   public static void getData(List<?> data) {
      System.out.println("data :" + data.get(0));
   }
}

输出:
data :icon
data :18
data :314
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,826评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,968评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,234评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,562评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,611评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,482评论 1 302
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,271评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,166评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,608评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,814评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,926评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,644评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,249评论 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,866评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,991评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,063评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,871评论 2 354

推荐阅读更多精彩内容

  • Java集合类可用于存储数量不等的对象,并可以实现常用的数据结构如栈,队列等,Java集合还可以用于保存具有映射关...
    小徐andorid阅读 1,941评论 0 13
  • 1.Java集合框架是什么?说出一些集合框架的优点? 每种编程语言中都有集合,最初的Java版本包含几种集合类:V...
    Oneisall_81a5阅读 901评论 0 11
  • 1.Java集合框架是什么?说出一些集合框架的优点? 每种编程语言中都有集合,最初的Java版本包含几种集合类:V...
    胖先森阅读 810评论 4 17
  • title: java集合框架学习总结 tags:集合框架 categories:总结 date: 2017-03...
    行径行阅读 1,685评论 0 2
  • 致橡树 我如果爱你—— 绝不像攀援的凌霄花, 借你的高枝炫耀自己; 我如果爱你—— 绝不学痴情的鸟儿...
    叫我理科生ella阅读 43评论 0 0