——Java培训、Android培训、iOS培训、.Net培训、期待与您交流! ——-
集合
Java程序中有着很多的对象,为了方便对多个对象的操作,就对对象进行存储,集合就是存储对象最常用的一 种方式。
数组与集合的不同:
1、 数组长度不可变,集合的长度可变
2、 数组可以储存对象与基本数据类型,集合只能储存对象
3、 数组只能储存一种数据类型,集合储存的是Object对象
集合的框架:
这次我们只怎对Collection类以及子类作介绍:
Collection接口
集合作为一个储存数据的接口,定义了一些对数据操作的方法,接口的子类通过重写该接口的方法实现对数据的操作。
1,添加元素
add(e);
addAll(collection);
2,删除元素
remove(e);
removeAll(collection);
clear();
3,对元素进行判断。
contains(e);
isEmpty();
4,获取元素
iterator();
size();
5,获取交集。
retainAll();
6,集合变数组。
toArray();
迭代器:
在Collection接口中有一个内部接口iterator接口,该接口提供了对集合内部数据访问的函数,该函数的实现类根据类内部的数据存储结构重写,操作方法:
hasNext();//有下一个元素,返回真
next();//取出下一个元素
remove();//移除
Colletion 的两个子接口List、Set
List:元素是有序的,元素可以重复。因为该集合体系有索引。
Set:元素是无序的,元素不可以重复。
List的子类:
ArrayList 类:实现List接口,底层的数据结构使用的是数组结构,查询速度很快。但是增删稍慢。线程不同步
LinkedList类:底层使用的是链表数据结构,增删速度很快,查询稍慢。
我们通过迭代与索引两种方法或的集合数据:
/**
* 用迭代获得数据
*
*/
public class Test12 {
public static void main(String[] args) throws InterruptedException {
ArrayList<String> list = new ArrayList<String>();
//加进数据
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.add("e");
//用迭代获得数据
Iterator<String> iter = list.iterator();
while(iter.hasNext())
{
System.out.println(iter.next());
}
}
}
/**
* 用索引获得数据
*
*/
public class Test12 {
public static void main(String[] args) throws InterruptedException {
ArrayList<String> list = new ArrayList<String>();
//加进数据
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.add("e");
//用迭代获得数据
for(int i= 0;i<list.size();i++)
{
System.out.println(list.get(i));
}
}
}
Set子类:
HashSet:底层数据结构是哈希表。线程不同步。 保证元素唯一性的原理:判断元素的hashCode值是否相同。如果相同,还会继续判断元素的equals方法,是否为true。
TreeSet:可以对Set集合中的元素进行排序。默认按照字母的自然排序。底层数据结构是二叉树。保证元素唯一性的依据:compareTo方法return 0。
练习一:
/**
* 往hashSet集合中存入自定对象
*姓名和年龄相同为同一个人,重复元素。
*
*/
public class Test12 {
public static void main(String[] args) throws InterruptedException {
HashSet<Person1> set = new HashSet<Person1>();
set.add(new Person1("张三",15));
set.add(new Person1("李四",15));
set.add(new Person1("王五",19));
set.add(new Person1("王五",18));
set.add(new Person1("张三",15));
Iterator<Person1> iter = set.iterator();
while(iter.hasNext())
{
System.out.println(iter.next());
}
}
}
class Person1
{
private String name = null;
private int age = 0;
public Person1(String name,int age)
{
this.name = name;
this.age = age;
}
//重写hashCode
@Override
public int hashCode() {
return name.hashCode()+age*20;
}
//重写equals方法
@Override
public boolean equals(Object obj) {
if(!(obj instanceof Person1))
return false;
Person1 p = (Person1)obj;
return this.name.equals(p.name) && this.age == p.age;
}
@Override
public String toString() {
return "Person [name=" + name + ", age=" + age + "]";
}
}
运行结果:
从结果看到名字与年龄相同的为一个人,元素没有重复。
对TreeSet方法进行排序,方法一
实现Comparable接口,并重写compareTo方法,在该方法在定义比较的标准。
/**
* 用TreeSet对对象进行排序
*按年龄大到小、年龄相同按名字排
*
*/
public class Test12 {
public static void main(String[] args) throws InterruptedException {
TreeSet<Person1> set = new TreeSet<Person1>();
set.add(new Person1("张三",15));
set.add(new Person1("李四",15));
set.add(new Person1("王五",19));
set.add(new Person1("王五",18));
set.add(new Person1("张三",15));
Iterator<Person1> iter = set.iterator();
//打印对象
while(iter.hasNext())
{
System.out.println(iter.next());
}
}
}
class Person1 implements Comparable<Person1>
{
private String name = null;
private int age = 0;
public Person1(String name,int age)
{
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person [name=" + name + ", age=" + age + "]";
}
//重写Comparable中的比较方法
@Override
public int compareTo(Person1 o) {
int num =o.age - this.age;
if(num==0)
num = this.name.compareTo(o.name);
return num;
}
}
结果:
方法二:实现Comparator接口,重写比较方法,把该接口的子类对象作为参数传到TreeSet的构造函数上。
/**
* 用TreeSet对对象进行排序
*按年龄大到小、年龄相同按名字排
*
*/
public class Test12 {
public static void main(String[] args) throws InterruptedException {
//定义匿名内部类作为参数专递
TreeSet<Person1> set = new TreeSet<Person1>(new Comparator<Person1>() {
@Override
public int compare(Person1 o1, Person1 o2) {
int num =o2.getAge() - o1.getAge();
if(num==0)
num = o1.getName().compareTo(o2.getName());
return num;
}
});
set.add(new Person1("张三",15));
set.add(new Person1("李四",15));
set.add(new Person1("王五",19));
set.add(new Person1("王五",18));
set.add(new Person1("张三",15));
Iterator<Person1> iter = set.iterator();
//打印对象
while(iter.hasNext())
{
System.out.println(iter.next());
}
}
}
class Person1
{
private String name = null;
private int age = 0;
public Person1(String name,int age)
{
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person [name=" + name + ", age=" + age + "]";
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
结果:
可见两种方法有着相同的作用,当两种方法同时用是,只有方法二起作用。