集合
回顾练习题
TreeSet
- 1.使用Employee实现Comparable接口,并按name排序
2.创建TreeSet时传入Comparator对象,按生日日期的先后顺序排序
MyDate类:
private成员变量yaer,month,day,并定义每一个属性定义getter,setter方法
定义一个Employee类
包含:private成员包括name,age,birthday,birthday是MyDate类的对象
重写toString方法输出name,age,birthday
package set;
import java.util.Comparator;
import java.util.Iterator;
import java.util.TreeSet;
/*
1.使用Employee实现Comparable接口,并按name排序
2.创建TreeSet时传入Comparator对象,按生日日期的先后顺序排序
MyDate类:
private成员变量yaer,month,day,并定义每一个属性定义getter,setter方法
定义一个Employee类
包含:private成员包括name,age,birthday,birthday是MyDate类的对象
重写toString方法输出name,age,birthday
*/
public class TreeSetExercise {
//1.按名字排
public void test(){
TreeSet set = new TreeSet();
Employee e1 = new Employee("liudehua",55,new MyDate(1965,5,4));
Employee e2 = new Employee("zhangxueyou",45,new MyDate(1987,5,4));
Employee e3 = new Employee("guofucheng",43,new MyDate(1987,5,9));
Employee e4 = new Employee("liming",51,new MyDate(1954,7,3));
Employee e5 = new Employee("liuxiang",23,new MyDate(1997,12,12));
set.add(e1);
set.add(e2);
set.add(e3);
set.add(e4);
set.add(e5);
//遍历
//方式一(好)
Iterator iterator = set.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
}
//方式二
// for (Object o : set) {
// System.out.println(o);
// }
}
//2.按生日排(定制排)
public void test1(){
TreeSet set = new TreeSet(new Comparator() {
@Override
public int compare(Object o1, Object o2) {
if (o1 instanceof Employee && o2 instanceof Employee){
Employee employee1 = (Employee) o1;
Employee employee2 = (Employee) o2;
MyDate b1 = employee1.getBirthday();
MyDate b2 = employee2.getBirthday();
//比较年
int minusYear = b1.getYear() - b2.getYear();
if (minusYear !=0){
return minusYear;
}else {//比较月
int minusMonth = b1.getMonth() - b2.getMonth();
if (minusMonth !=0){
return minusMonth;
}//比较日
int minusDay = b1.getDay() - b2.getDay();
return minusDay;
}
}
//return 0;
throw new RuntimeException("输入的数据不一致");
}
});
Employee e1 = new Employee("liudehua",55,new MyDate(1965,5,4));
Employee e2 = new Employee("zhangxueyou",45,new MyDate(1987,5,4));
Employee e3 = new Employee("guofucheng",43,new MyDate(1987,5,9));
Employee e4 = new Employee("liming",51,new MyDate(1954,7,3));
Employee e5 = new Employee("liuxiang",23,new MyDate(1997,12,12));
set.add(e1);
set.add(e2);
set.add(e3);
set.add(e4);
set.add(e5);
Iterator iterator = set.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
}
}
//测试
public static void main(String[] args) {
TreeSetExercise treeSetExercise = new TreeSetExercise();
treeSetExercise.test1();
}
}
package set;
/*
private成员变量yaer,month,day,并定义每一个属性定义getter,setter方法
*/
public class MyDate {
private int year;
private int month;
private int day;
public MyDate() {
}
public MyDate(int year, int age, int day) {
this.year = year;
this.month = age;
this.day = day;
}
public int getYear() {
return year;
}
public void setYear(int year) {
this.year = year;
}
public int getMonth() {
return month;
}
public void setMonth(int month) {
this.month = month;
}
public int getDay() {
return day;
}
public void setDay(int day) {
this.day = day;
}
@Override
public String toString() {
return "MyDate{" +
"year=" + year +
", month=" + month +
", day=" + day +
'}';
}
}
package set;
/*
定义一个Employee类
包含:private成员包括name,age,birthday,birthday是MyDate类的对象
重写toString方法输出name,age,birthday
*/
public class Employee implements Comparable {
private String name;
private int age;
private MyDate birthday;
public Employee() {
}
public Employee(String name, int age, MyDate birthday) {
this.name = name;
this.age = age;
this.birthday = birthday;
}
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;
}
public MyDate getBirthday() {
return birthday;
}
public void setBirthday(MyDate birthday) {
this.birthday = birthday;
}
@Override
public String toString() {
return "Employee{" +
"name='" + name + '\'' +
", age=" + age +
", birthday=" + birthday +
'}';
}
//按照姓名排自然顺序
@Override
public int compareTo(Object o) {
if (o instanceof Employee){
Employee employee = (Employee) o;
return this.name.compareTo(employee.name);//当前.name.compareTo()
}else {
throw new RuntimeException("输入数据不一致");
}
}
}
Set课后面试题
- 练习一:在List内去除重复数字值,要求尽量简单
package list;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
/*
在List内去除重复数字值,要求尽量简单
如果是自定义类,需要重写equals()和hashCode()方法
*/
public class Demo1 {
public static List dublicateList(List list){
HashSet set = new HashSet();
set.addAll(list);
return new ArrayList(set);
}
public static void main(String[] args) {
ArrayList list = new ArrayList();
list.add(new Integer(1));
list.add(new Integer(2));
list.add(new Integer(2));
list.add(new Integer(3));
list.add(new Integer(4));
list.add(new Integer(4));
List list1 = dublicateList(list);
for (Object o : list1) {
System.out.println(o);
}
}
}
- 练习二:set中的添加元素过程
public void test2(){
HashSet set = new HashSet();
Mouse p1 = new Mouse("AA", 1001);
Mouse p2 = new Mouse("BB", 1002);
set.add(p1);
set.add(p2);
p1.name = "CC";
set.remove(p1);//先改过名字的hash值
System.out.println(set);//没有删除,因为hash值不同
set.add(new Mouse("CC",1001));
System.out.println(set);//计算一个新的hash值存到一个数组上
set.add(new Mouse("AA",1001));
System.out.println(set);//还是添加成功
}
Map接口
-
实现类:
-
HashMap,其子类:
- LinkedHashMap
-
SortedMap,其子类:
- TreeMap
-
Hashtable,其子类:
- Properties
-
-
Map接口:双列数据,存储key-value对的数据 ----类似于高中的函数:y = f(x)
HashMap底层结构:jdk8中:数组+链表+红黑树
HashMap:作为Map主要的实现类:线程不安全,效率高;存储null的key和value,扩容为原来的两倍
子类:LinkedHashMap:保证在遍历map元素时,可以按照添加的顺序实现遍历
原因:在原有的HashMap底层结构基础上,添加一对指针,指向前一个和后一个
对于频繁的遍历操作,此类执行效率高于HashMap
TreeMap:保证按照添加的key-value对进行排序,实现排序遍历。
此时考虑key的自然排序或定制排序。
底层结构:使用红黑树
Hashtable:作为古老的实现类:线程安全,效率低;不能存储null的key和value
子类:Properties:常用来处理配置文件。key和value都是String类型
面试题
-
面试三个题:
-
HashMap的底层实现原理?
jdk7中:
HashMap map = new HashMap();
1.实例化后底层创建了长度是16的一维数组Entry[] table。
…可能已经执行过多次put…
2.map.put(key1,value1):
首先调用key1所在类的hashCode()计算key1哈希值,此哈希值经过某种算法计算得到Entry数组中的存放位置。
如果此位置上数据为空,此时key1,value1添加成功
如果此位置上有数据,比较key1和已经存在的一个或多个数据的哈希值(以链表形式存在):
如果哈希值都不相同,key1-value1添加成功
如果key1哈希值和某一个数据(key2-value2)的哈希值相同,调用key1所在类的equals(key2)方法比较:
如果equals()返回false,key1-value1添加成功
如果equals()返回ture,使用value1替换value2jdk8中:
1.new HashMap():底层没有创建一个长度为16的数组
2.jdk8底层的数组不是Entry[],而是Node[]
3.首次调用put()方法时,底层创建长度为16的数组
4。底层结构:数组+链表+红黑树,
当数组某一个索引位置上的元素以链表形式存在的数据个数>8,且当前数组的长度>64,
此索引位置上所有数据改为红黑树存储。 -
HashMap和Hashtable的区别?
HashMap:主要的实现类,线程不安全,效率高,存储null的key和value
Hashtable:线程安全,效率低,不能存储null的key和value
-
ConcurrentHashMap 与Hashtable的异同?
-
1.HashMap是线程不安全的,ConcurrentHashMap是线程安全的
2.ConcurrentHashMap将整个hash桶进行了分段segment,每个分段上都有锁存在,当一个线程
访问其中一个数据片段时,其他的数据也能够被其他线程访问。
3.ConcurrentHashMap让锁的力度更精细,并发性能更好
4.ConcurrentHashMap不能存储null键值对,HashMap可以存储null键值对 -
谈谈你对HashMap中put/get方法的认识?
-
put方法可以作为增加数据,也可以用于修改value值,get方法获取指定key对应的value
-
谈谈HashMap的扩容机制?默认大小是多少?
提前扩容:先看超出临界值(12)所处的数组位置是否空,空就不扩容,非空就开始扩容,扩容为原来的2倍,并返回原来的数据
DEFAULT_INITIAL_CAPACITY:HashMap的默认容量:16
-
什么是加载因子(或填充比)?
DEFAULT_LOAD_FACTOR:HashMap的默认加载因子决定了数据密度:0.75,加载因子太小,比如0.3,乘以16后变成4就要扩容,意味着数组利用率低,太大数组的链表结构又太多,造成查询或插入时的比较次数多,性能下降
-
什么是吞吐临界值(或阈值、threshold)?
TREEIFY_THRESHOLD:Bucket中链表长度大于该默认值,转化为红黑树:8
*threshold:扩容的临界值 =默认容量(16)填充因子(0.75)=> 12
-
-
Map接口
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-03FkZh7D-1652253511669)(C:\Users\liuxiang\AppData\Roaming\Typora\typora-user-images\image-20220313210216898.png)]
- put(key,value):看上去是放入的双列数据,其实还是放入的是一个数据(Entry对象),Entry当中有两个属性:key和value。Entry是不可重复的,无序的,可以理解用Set来承装,Key是不可重复的,无序的,理解用Set来承装,Value是重复的,无序的,简单理解用Colletion来承装。
HashMap的底层实现原理
- jdk7中:
- HashMap map = new HashMap();
1.实例化后底层创建了长度是16的一维数组Entry[] table。
…可能已经执行过多次put…
2.map.put(key1,value1):
首先调用key1所在类的hashCode()计算key1哈希值,此哈希值经过某种算法计算得到Entry数组中的存放位置。
如果此位置上数据为空,此时key1,value1添加成功
如果此位置上有数据,比较key1和已经存在的一个或多个数据的哈希值(以链表形式存在):
如果哈希值都不相同,key1-value1添加成功
如果key1哈希值和某一个数据(key2-value2)的哈希值相同,调用key1所在类的equals(key2)方法比较:
如果equals()返回false,key1-value1添加成功
如果equals()返回ture,使用value1替换value2. - jdk8中:
1.new HashMap():底层没有创建一个长度为16的数组
2.jdk8底层的数组不是Entry[],而是Node[]
3.首次调用put()方法时,底层创建长度为16的数组
4。底层结构:数组+链表+红黑树,
当数组某一个索引位置上的元素以链表形式存在的数据个数>8,且当前数组的长度>64,
此索引位置上所有数据改为红黑树存储。
HashMap存储结构
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-tZreRW3x-1652253511670)(C:\Users\liuxiang\AppData\Roaming\Typora\typora-user-images\image-20220315160451879.png)]
HashMap源码分析(JDK8)
1.HashMap构造器:
piblic HashMap(){
this.loadFactor = DEFAULT_LOAD_FACTOR;//家住因子赋值为0.75,没有创建数组
}
2.用了Node()代替Entry()
static class Node<K,V> implements Map.Entry<K,V>{
final int hash;
final K key;
V value;
Node<K,V> next;//LinkedHashMap继承了HashMap,能够记录添加元素先后(before、after)顺序,
Node(int hash,K key,V value,Node<K,V> next){
this.hash = hash;
this.key = key;
this.value = value;
this.next = next;
}
}
3.put(key,value)方法:
public V put(K key,V value){
return putVal(hash(key),key,value,false,true);
}
4.hash值:
static final int hash(Object key){
int h;
return (key == null) ? 0 : (h= key.hashCode())^(h >> 16);
}
4.putVal
final V putVal(int hash,K key,V value,boolean onlyIfAbsent,
boolean evict){
Node<K,V>[] tab;Node<K,V> p;int n,i;//声明两个变量是Node类型
if((tab = table) == null || (n = tab.length) == 0)//有一个为真就进行
n= (tab = resize()).length;//resize()扩容,不是首次添加此if不考虑
if((p = tab[i = (n-1) & hash]) == null)
tab[i] = newNode(hash,key,value,null);//如果数组上没有数据,添加成功
else{//如果数组上有值
Node<K,V> e;K k;
if(p.hash == hash &&((k = p.key) == key || (key != null && key.equals(k))))//如果哈希值一样,且equals()也一样
e = p;//
else if(p instanceof TreeNode)
e = ((TreeNode<K,V>)p).putTreeVal(this,tab,hash,key,val)
else{
for(int binCount = 0;;++binCount){
if((e =p,next) == null){//说明只有一个元素p
p.next = newNode(hash,key,value,null);//新造一个
if(binCount >= TREEIFY_THRESHOLD-1)
treeifyBin(tab,hash);//当长度大于8且数组长度>64就要变成红黑树
break;
}
if(e.hash == hash &&
((k =e.key) == key || (key != null && key.equals(k))))
break;
p = e;//返回,一直考虑下一个元素,对比哈希值和equals()方法
}
}
if(e != null){//替换value
V oldValue = e.value;
if(!onlyIfAbsent || oldValue == null)
e.value = value;
afterNodeAccess(e);
return oldValue;
}
}
++modCount;
if(++size > threshold)
resize();
}
5.resize():扩容
//newCap = 16;
// newThr = (int){0.75*16=12};===临界值threshold
//new Node[newCap]:造好数组===table
Map中常用方法
package Map;
import java.util.*;
/*
一、
Map接口:双列数据,存储key-value对的数据 ----类似于高中的函数:y = f(x)
HashMap底层结构:jdk8中:数组+链表+红黑树
HashMap:作为Map主要的实现类:线程不安全,效率高;存储null的key和value,扩容为原来的两倍。
子类:LinkedHashMap:保证在遍历map元素时,可以按照添加的顺序实现遍历
原因:在原有的HashMap底层结构基础上,添加一对指针,指向前一个和后一个
对于频繁的遍历操作,此类执行效率高于HashMap
TreeMap:保证按照添加的key-value对进行排序,实现排序遍历。
此时考虑key的自然排序或定制排序。
底层结构:使用红黑树
Hashtable:作为古老的实现类:线程安全,效率低;不能存储null的key和value
子类:Properties:常用来处理配置文件。key和value都是String类型
二、Map结构的理解:
Map中的key:无序的,不可重复的,使用Set存储所有的key,--自定义类要求key所在的类重写equals()和hashCode()方法
Map中的value:无序的,可重复的,使用Collection存储所有的value ---value自定义类要重写equals()方法
一个键对值:key-value构成了一个Entry对象
Map中的entry:无序的,不可重复的,使用Set存储所有的key
三、HashMap的底层实现原理:
jdk7中:
HashMap map = new HashMap();
1.实例化后底层创建了长度是16的一维数组Entry[] table。
..可能已经执行过多次put...
2.map.put(key1,value1):
首先调用key1所在类的hashCode()计算key1哈希值,此哈希值经过某种算法计算得到Entry数组中的存放位置。
如果此位置上数据为空,此时key1,value1添加成功
如果此位置上有数据,比较key1和已经存在的一个或多个数据的哈希值(以链表形式存在):
如果哈希值都不相同,key1-value1添加成功
如果key1哈希值和某一个数据(key2-value2)的哈希值相同,调用key1所在类的equals(key2)方法比较:
如果equals()返回false,key1-value1添加成功
如果equals()返回ture,使用value1替换value2(修改)
jdk8中:
1.new HashMap():底层没有创建一个长度为16的数组
2.jdk8底层的数组不是Entry[],而是Node[]
3.首次调用put()方法时,底层创建长度为16的数组
4。底层结构:数组+链表+红黑树,
当数组某一个索引位置上的元素以链表形式存在的数据个数>8,且当前数组的长度>64,
此索引位置上所有数据改为红黑树存储。
总结:常用方法:
增:put(Object key,Object value)
删:remove(Object key)
修改:put(Object key,Object value)
查询:get(Object key)
长度:size()
遍历:map.keySet()
map.values()
map.entrySet()
*/
public class MapTest {
public void test(){
HashMap map = new HashMap();
//1.添数据 void.put(key,value)
map.put("AA",123);
map.put("BB",183);
map.put(23,123);
//修改作用
map.put("AA",67);
System.out.println(map);
HashMap map1 = new HashMap();
map.put("CC",123);
map.put("DD",123);
//2.putAll(m)将map1中的所有key-value放入当前map中
map.putAll(map1);
System.out.println(map);
//3.remove(Object key):移除key对象,并返回key对应的value值,没有的话就返回null
Object value = map.remove("CC");
System.out.println(value);
System.out.println(map);
//4.clear():清空
// map.clear();
// System.out.println(map);
// System.out.println(map.size());//0
//8.isEmpty():判断当前map是否为空
System.out.println(map.isEmpty());
//5.Object get(Object key):获取指定key对应的value
System.out.println(map.get(23));
//6.boolean containsKey(Object key):是否包含指定的key
boolean isExist = map.containsKey("DD");
System.out.println(isExist);
//6.int size():获取map中key-value对的个数
System.out.println(map.size());
//7.boolean equals(Object obj):判断当前map和参数对象obj是否相等
System.out.println(map.equals(map1));//false
}
//遍历
public void test1(){
//1.拿到所有的key可以用set.iterator遍历(无序,不可重复的)
//2.拿到所有的value可以用collection.iterator遍历(无序,可重复的)
//3.拿到所有的key-value对,可以用set.iterator遍历(无序,不可重复的)
HashMap map = new HashMap();
map.put("AA",123);
map.put(45,88);
map.put("BB",45);
//遍历所有的key集,map.keySet()
Set set = map.keySet();
Iterator iterator = set.iterator();
while (iterator.hasNext()){
//System.out.println(iterator.next());
//直接用get(key)方法获得value
Object key = iterator.next();
System.out.println(key);
Object value = map.get(key);
System.out.println(key + "===" +value);
}
System.out.println("======================");
//遍历所有的value集,map.values()
Collection values = map.values();
Iterator iterator1 = values.iterator();
while (iterator1.hasNext()){
System.out.println(iterator1.next());
}
System.out.println("======================");
//遍历所有的key-value对,map.entrySet(),集合中元素都是entry
Set set1 = map.entrySet();
Iterator iterator2 = set1.iterator();
while (iterator2.hasNext()){
Object obj = iterator2.next();
//强制转化,利用内部类定义的方法
Map.Entry entry = (Map.Entry)obj;
System.out.println(entry.getKey() +"-->" + entry.getValue());
}
}
//测试
public static void main(String[] args) {
MapTest mapTest = new MapTest();
mapTest.test1();
}
}
TreeMap
-
向TreeMap中添加key-value,要求key必须是由同一个类创建的对象
-
因为要按照key进行排序:自然排序,定制排序
package Map;
import collection.User;
import java.util.*;
/*
- **向TreeMap中添加key-value,要求key必须是由同一个类创建的对象**
- **因为要按照key进行排序:自然排序Comparable,定制排序Comparator**
*/
public class TreeMapTest {
//自然排序
public void test(){
TreeMap map = new TreeMap();
User u1 = new User("Tom", 23);
User u2 = new User("Jerry", 33);
User u3 = new User("Jack", 20);
User u4 = new User("Rose", 15);
map.put(u1,98);
map.put(u2,89);
map.put(u3,58);
map.put(u4,108);
Set set = map.entrySet();
Iterator iterator = set.iterator();
while (iterator.hasNext()){
Object obj = iterator.next();
Map.Entry entry = (Map.Entry) obj;
System.out.println(entry.getKey() +"---->" +entry.getValue());
}
}
//定制排序
public void test1(){
TreeMap map = new TreeMap(new Comparator() {
@Override
public int compare(Object o1, Object o2) {
if (o1 instanceof User && o2 instanceof User){
User user1 = (User) o1;
User user2 = (User) o2;
return Integer.compare(user1.getAge(),user2.getAge());
}
//return 0;
throw new RuntimeException("输入数据不一致");
}
});
User u1 = new User("Tom", 23);
User u2 = new User("Jerry", 33);
User u3 = new User("Jack", 20);
User u4 = new User("Rose", 15);
map.put(u1,98);
map.put(u2,89);
map.put(u3,58);
map.put(u4,108);
Set set = map.entrySet();
Iterator iterator = set.iterator();
while (iterator.hasNext()){
Object obj = iterator.next();
Map.Entry entry = (Map.Entry) obj;
System.out.println(entry.getKey() +"---->" +entry.getValue());
}
}
//测试
public static void main(String[] args) {
TreeMapTest treeMapTest = new TreeMapTest();
treeMapTest.test1();
}
}
Properties
- 常用来处理配置文件,key和value都是String类型
package Map;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Properties;
//Properties:常用来处理配置文件,key和value都是String类型
//点文件右键+create resource bundle==直接创建配置文件(用java调用数据库)
public class PropertiesTest {
public static void main(String[] args) {
//ctrl+alt+t:try-catch
try {
Properties pros = new Properties();
FileInputStream fis = new FileInputStream("jdbc.properties");
pros.load(fis);//加载流对应的文件
String name = pros.getProperty("name");
String password = pros.getProperty("password");
System.out.println("name = " + name +", password = " +password);
} catch (IOException e) {
e.printStackTrace();
} finally {
}
}
}
Collection工具类
- 面试题:
Collection:是一个存储单列数据的集合接口,常见子接口:list、set
Collections:是一个工具类 - Collections类中提供了多个synchronizedXxx()方法,此方法可以将指定集合包装成线程同步的集合,可以解决线程不安全问题
/*
Collections:操作Collection、Map的工具类
面试题:
Collection:是一个存储单列数据的集合接口,常见子接口:list、set
Collections:是一个工具类
方法:
reverse(List):反转List中元素的顺序
shuffle(List):对List集合元素进行随机排序
sort(List):根据元素的自然顺序对指定List集合元素按升序排序
sort(List,Comparator):根据指定的Comparator产生的顺序对List集合元素进行排序
swap(List,int i,int j):将指定List集合中的i处元素和j处元素进行交换
Object max(Collection):根据元素的自然顺序,返回给定集合中的最大元素
Object max(Collection,Comparator):根据Comparator指定的顺序,返回给定集合中的最大元素
Object min()
int frequency(Collection,Object):返回指定集合中指定元素的出现次数
void copy(List dest,List src):将src中的内容复制到dest中
boolean replaceAll(List list,Object oldVal,Object newVal):使用新值替换List中的旧值
*/
import java.lang.reflect.Array;
import java.util.*;
public class CollectionsTest {
public void test(){
ArrayList list = new ArrayList();
list.add(123);
list.add(43);
list.add(13);
list.add(13);
list.add(-3);
list.add(0);
System.out.println(list);
//1.reverse(List):反转List中元素的顺序
Collections.reverse(list);
System.out.println(list);
//2.shuffle(List):对List集合元素进行随机排序
Collections.shuffle(list);
System.out.println(list);
//3.sort(List):根据元素的自然顺序对指定List集合元素按升序排序
Collections.sort(list);
System.out.println(list);
//4.swap(List,int i,int j):将指定List集合中的i处元素和j处元素进行交换
Collections.swap(list,1,2);
System.out.println(list);
//5.Object max(Collection):根据元素的自然顺序,返回给定集合中的最大元素
//6.int frequency(Collection,Object):返回指定集合中指定元素的出现次数
int frequency = Collections.frequency(list, 13);
System.out.println(frequency);
//7.void copy(List dest,List src):将src中的内容复制到dest中,保证dest的长度不小于list
//size指的是填了几个数组
//异常写法:IndexOfBoundsException
// ArrayList dest = new ArrayList();
// Collections.copy(dest,list);
//正确写法:将size撑开:造一个数组,数组长度是list.size,有size个元素,每个位置都是null
List<Object> dest = Arrays.asList(new Object[list.size()]);
System.out.println(dest.size());
Collections.copy(dest,list);
System.out.println(dest);
}
/*
**Collections类中提供了多个synchronizedXxx()方法,
*此方法可以将指定集合包装成线程同步的集合,可以解决线程不安全问题**
*/
public void test1(){
ArrayList list = new ArrayList();
list.add(123);
list.add(43);
list.add(13);
list.add(13);
list.add(-3);
list.add(0);
//用此方法返回的list1就是线程安全的list
List list1 = Collections.synchronizedList(list);
}
//测试
public static void main(String[] args) {
CollectionsTest collectionsTest = new CollectionsTest();
collectionsTest.test();
}
}
练习题
1.请从键盘随机输入10个整数保存到List中,并按倒序、从大到小的顺序显示出来。
import java.util.*;
public class Exer {
public void test(){
Scanner scanner = new Scanner(System.in);
ArrayList list = new ArrayList();
System.out.println("随机输入十个整数:");
for (int i = 0; i < 10; i++) {
int number = scanner.nextInt();
list.add(number);
}
System.out.println(list);
//从大到小排列
Collections.sort(list);//从小到大
Collections.reverse(list);
//遍历集合
Iterator iterator = list.iterator();
while (iterator.hasNext()){
System.out.print(iterator.next() +" ");
}
}
//自己写打印方法
// public static void test1(int[] a){
// for (int i = 0; i < a.length; i++) {
// if (i == 0){
// System.out.println("[");
// }if (i == a.length-1){
// System.out.println(a[i] + "]");
// }else {
// System.out.println(a[i] + " ");
// }
// }
// }
//
public static void main(String[] args) {
Exer exer = new Exer();
exer.test();
}
}
2.请把学生名与考试分数录入到集合中,并按分数显示前三名成绩学员的名字。
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.Set;
/*
请把学生名与考试分数录入到集合中,并按分数显示前三名成绩学员的名字。
*/
public class Exer1 {
public void test() {
HashMap<String,Integer> map = new HashMap<String,Integer>();
map.put("张三", 60);
map.put("李四", 70);
map.put("赵五", 80);
map.put("杜六", 90);
map.put("钱八", 85);
map.put("孙九", 50);
Set<String> nameSet = map.keySet();
ArrayList<String> name = new ArrayList<>();//创建name集合
ArrayList<Integer> score = new ArrayList<>();//创建分数集合
//遍历并存储到集合当中去
for (String o : nameSet) {
name.add(o);
score.add(map.get(o));
}
//成绩排序
for (int i = 0; i < score.size(); i++) {
for (int j = i +1; j < score.size(); j++) {
if (score.get(i) < score.get(j)){
Collections.swap(score,i,j);
Collections.swap(name,i,j);
}
}
}
System.out.println("成绩前三名:");
for (int i = 0; i < 3; i++) {
System.out.println("姓名:" +name.get(i) +",成绩:" + score.get(i));
}
}
//测试
public static void main(String[] args) {
Exer1 exer1 = new Exer1();
exer1.test();
}
}
3.对一个java源文件中 关键字进行计数。提示:将所有的关键字保存在一个HashSet中,用contains()来测试
File file = new File("Test.java");
Scanner scanner = new Scanner(file);
while(scanner.hasNext()){
String word = scanner.next();
System.out.println(word);
}
String o : nameSet) {
name.add(o);
score.add(map.get(o));
}
//成绩排序
for (int i = 0; i < score.size(); i++) {
for (int j = i +1; j < score.size(); j++) {
if (score.get(i) < score.get(j)){
Collections.swap(score,i,j);
Collections.swap(name,i,j);
}
}
}
System.out.println(“成绩前三名:”);
for (int i = 0; i < 3; i++) {
System.out.println(“姓名:” +name.get(i) +“,成绩:” + score.get(i));
}
}
//测试
public static void main(String[] args) {
Exer1 exer1 = new Exer1();
exer1.test();
}
}
**3.对一个java源文件中 关键字进行计数。提示:将所有的关键字保存在一个HashSet中,用contains()来测试**
```java
File file = new File("Test.java");
Scanner scanner = new Scanner(file);
while(scanner.hasNext()){
String word = scanner.next();
System.out.println(word);
}