可变参数,Collections,Map集合,Stream

(1)可变参数

可变参数:就是一种特殊形参,定义在方法、构造器的形参列表里

                  格式:数据类型...参数名称;

                  特点:可以不传数据给它;可以传一个或者同时传多个数据给它;也可以传一个数组给它

                  好处:常常用来灵活的接收数据

    public static void main(String[] args) {
        test();
        test(10);
        test(10,20,30);
        test(new int[]{10,20,30,40});
    }
    public static void test(int...nums){
        System.out.println(nums.length);
        System.out.println(Arrays.toString(nums));
        System.out.println("-----------------------------------");
    }

注意事项  1:一个形参列表中,只能有一个可变参数

                 2:可变参数必须放在形参列表的最后面     (int age,int nums)

(2)Collections

Collection:是一个用来操作集合的工具类

方法名称说明
public static <T> boolean addAl1(Collection<? super T> c, T... elements)给集合批量添加元察
public static void shuffle(List<?> list)打乱List集合中的元素顺序
打乱List集合中的元素顺序对List集合中的元素进行升序排序
public static <T> void sort(List<T> list,Comparator<? super T> c)对List集合中元素,按照比较器对象指定的规则进行排序

Collections只支持对List集合进行排序

排序方式1:

方法名称说明
public static <T> void sort(List<T> list)对List集合中元素按照默认规则排序

注意:本方法可以直接对自定义类型的List集合排序,但自定义类型必须实现了Comparable接口,指定了比较规则才可以

排序方法2:

方法名称说明
public static <T> void sort(List<T> list,comparator<? super T> c)对List集合中元素,按照比较器对象指定的规则进行排序

(3)Map集合

Map集合称为双列集合,格式: {key1=value1 , key2=value2, key3=value3 , ...},一次需要存一对数据作为一个元素

Map集合的每个元素“key=value”称为一个键值对/键值对对象/一个Entry对象,Map集合也被叫做“键值对集合"

Map集合的所有键是不允许重复的,但值可以重复,键和值是一一对应的,每一个键只能找到自己对应的值

考虑一一对应的数据时:需要存储一一对应的数据时,就可以考虑使用Map集合来做

 Map集合的特点:

注意:Map系列集合的特点都是由键决定的,值只是一个附属品,值是不做要求的

HashMap(由键决定特点)︰无序、不重复、无索引;(用的最多)

LinkedHashMap (由键决定的特点):有序,不重复,无索引

TreeMap(有键决定特点):按照大小默认升序排序:不重复、无索引

        Map<String,Integer>map=new HashMap<>();//经典代码

        map.put("手表",100);
        map.put("手表",220);//后面重复的数据会覆盖前面的数据(键)
        map.put("书",2);
        map.put("Java",2);
        map.put(null,null);
        System.out.println(map);//{null=null, 手表=220, Java=2, 书=2}

1)Map的常用方法

Map是双列集合的祖宗,它的功能是全部双列集合都可以继承过来使用的

方法名称说明
public v put(K key,V value)添加元素
public int size()获取集合的大小
public void clear()清空集合
public boolean isEmpty()判断集合是否为空,为空返回true ,反之
public v get(Object key)根据键获取对应值(若无该键,返回null)
public v remove(0bject key)根据键删除整个元素
public boolean containsKey(Object key)判断是否包含某个键
public boolean containsValue(0bject value)判断是否包含某个值
public Set<K> keySet()获取全部键的集合
public collection<V> values()获取map集合的全部值

 补充:

public class ListTest1 {
    public static void main(String[] args) {
        Map<String,Integer>map1=new HashMap<>();
        map1.put("java1",10);
        map1.put("java2",20);
        Map<String,Integer>map2=new HashMap<>();
        map2.put("java3",10);
        map2.put("java2",222);
        map1.putAll(map2);//putAll:把map2集合的元素全部倒入一份到map1集合
        System.out.println(map1);//{java3=10, java2=222, java1=10}
        System.out.println(map2);//{java3=10, java2=222}
    }
}

(4)Map的遍历方式

Map集合的遍历方式说明
键找值先获取Map集合全部的键,再通过遍历键来找值
键值对把“键值对“看成一个整体进行遍历(难度较大)
LambdaJDK 1.8开始之后的新技术(非常的简单)

1)键找值

方法名称说明
public Set<K> keySet()获取所有键的集合
public v get(0bject key)根据键获取其对应的值
        Set<String>keys=map.keySet();
        for (String key:keys) {
            double value =map.get(key);
            System.out.println(key+"====>"+value);
        }

2)键值对

Map提供的方法说明
Set<Map.Entry<K, V> > entrySetO获取所有“键值对”的集合
        Set<Map.Entry<String,Double>> entries=map.entrySet();
        for (Map.Entry<String,Double>entry:entries) {
            String key=entry.getKey();
            double value=entry.getValue();
            System.out.println(key+"====>"+value);
        }

3)Lambda

方法名称说明
default void forEach(BiConsumer<? super K,? super v>action)结合lambda遍历Map集合
     map.forEach((k,v)->{
            System.out.println(k+"====>"+v);
        });

4)HashMap的底层原理

HashMap(由键决定特点)︰无序、不重复、无索引;(用的最多)

HashMap跟Hashset的底层原理是一模一样的,都是基于哈希表实现的

实际上:原来学的Set系列集合的底层就是基于Map实现的,只是Set集合中的元素只要键数据,不要值数据而已

HashMap的键依赖hashCode方法和equals方法保证键的唯一

如果键存储的是自定义类型的对象,可以通过重写hashCode和equals方法,这样可以保证多个对象内容一样时,HashMap集合就能认为是重复的

5)LinkedHashMap的底层原理

LinkedHashMap (由键决定的特点):有序,不重复,无索引

底层数据结构依然是基于哈希表实现的,只是每个键值对元素又额外的多了一个双链表的机制记录元素顺序(保证有序)

实际上:原来学习的LinkedHashSet集合的底层原理就是LinkedHashMap

6)TreeMap的底层原理

TreeMap(有键决定特点):按照大小默认升序排序:不重复、无索引

原理:TreeMap跟TreeSet集合的底层原理是一样的,都是基于红黑树实现的排序

TreeMap集合同样也支持两种方式来指定排序规则

让类实现Comparable接口,重写比较规则

TreeMap集合有一个有参数构造器,支持创建Comparator比较器对象,以便用来指定比较规则

 (5)集合的嵌套

集合的嵌套:指集合中的元素又是一个集合

import java.util.*;

public class ListTest1 {
    public static void main(String[] args) {
        Map<String,List<String>> map=new HashMap<>();

        List<String> cities1=new ArrayList<>();
        Collections.addAll(cities1,"南京市","扬州市","苏州市","无锡市","常州市");
        map.put("江苏省",cities1);
        System.out.println(map);//{江苏省=[南京市, 扬州市, 苏州市, 无锡市, 常州市]}
    }
}

(6)Stream

也叫Stream流,是Jdk8开始新增的一套APl(java.util.stream.*),可以用于操作集合或者数组的数据

优势: Stream流大量的结合了Lambda的语法风格来编程,提供了一种更加强大,更加简单的方式操作集合或者数组中的数据,代码更简洁,可读性更好

        //List
        List<String> names=new ArrayList<>();
        Collections.addAll(names,"张三丰","张无忌","周芷若","赵敏","张强");

        List<String> list=new ArrayList<>();
        for (String name:names) {
            if (name.startsWith("张")&&name.length()==3){
                list.add(name);
            }
        }



        //Stream流
        List<String> list2=names.stream().filter(s->s.startsWith("张")).filter(a->a.length()==3).collect(Collectors.toList());

1)Stream的使用步骤

 2)获取Stream流

【1】获取集合的Stream流

public interface Stream<T> ...{  }

Collection提供的如下方法说明
default Stream<E> stream()获取当前集合对象的Stream流
List<String> names=new ArrayList<>();
Collections.addAll(names,"张三丰","张无忌","周芷若","赵敏","张强");
Stream<String> stream=names.stream();

【2】获取数组的Stream流

Arrays类提供的如下方法说明
public static <T>Stream<T> stream(T[] array)获取当前数组的stream流
Stream类提供的如下方法说明
public static<T> Stream<T> of(T... values)获取当前接收数据的Stream流
        Set<String> set=new HashSet<>();
        Collections.addAll(set,"刘德华","张曼玉","蜘蛛精","马德","德玛西亚");
        Stream<String> stream1=set.stream();
        stream1.filter(s->s.contains("德")).forEach(s-> System.out.println(s));

【3】获取Map的Stream流

        Map<String,Double> map=new HashMap<>();
        Set<String> keys=map.keySet();
        Stream<String> ks=keys.stream();

        Collection<Double> values=map.values();
        Stream<Double> vs=values.stream();

        Set<Map.Entry<String,Double>>entries=map.entrySet();
        Stream<Map.Entry<String,Double>> kvs=entries.stream();

        kvs.filter(e->e.getKey().contains("巴")).forEach(e->System.out.println(e.getKey()+"---->"+e.getValue()));

【4】获取数组的Stream流

        String[]names2={"张三丰","张无忌","周芷若","赵敏","张强"};
        Stream<String> s1=Arrays.stream(names2);
        Stream<String> s2=Stream.of(names2);

3)Stream流常见的中间方法

中间方法指的是调用完成后会返回新的Stream流,可以继续使用(支持链式编程)

Stream提供的常用中间方法说明
Stream<T> filter( Predicate< ? super T> predicate)用于对流中的数据进行过滤
Stream<T> sorted(对元素进行升序排序
Stream<T> sorted(Comparator<? super T> comparator)按照指定规则排序
Stream<T> limit(long maxSize)获取前几个元素
Stream<T> skip(long n)跳过前几个元素
Stream<T> distinct()去除流中重复的元素
<R>Stream<R> map(Function<? super T,? extends R> mapper)对元素进行加工,并返回对应的新流
static <T> Stream<T> concat(Stream a,Stream b)合并a和b两个流为一个流
//数据
scores.stream().filter(s -> s >=60).sorted().forEach(s -> System.out.println(s));//升序


//对象
students.stream().filter(s -> s.getAge() >= 23 && s.getAge() <= 30).sorted((o1, o2)-> 02.getAge()- o1.getAge()).forEach(s -> System.out.println(s));//根据对象的年龄排序


//去身高最高的3位学生
students.stream().sorted((o1,o2) -> Double.compare(o2.getHeight(),o1.getHeight())).limit(3).forEach(s -> System.out.println(s));

students.stream().sorted((o1,o2) -> Double.compare(o2.getHeight(),o1.getHeight())).limit(3).forEach(System.out::println);


//身高最低的2名学生
students.stream().sorted((o1,o2) -> Double.compare(o2.getHeight(),o1.getHeight())).slip(students.size()-2).forEach(s -> System.out.println(s));



//找出身高超过168的学生叫什么名字,要求去除重复的名字
students.stream().filter(s -> s.getHeight() > 168).map(s->s.getName()).forEach(s -> system.out.println(s));

4)Strem流常见的终结方法

终结方法指的是调用完成后,不会返回新Stream了,没法继续使用流了

Stream提供的常用终结方法说明
void forEach(consumer action)对此流运算后的元素执行遍历
long count()统计此流运算后的元素个数
Optional<T>max(Comparator<? super T> comparator)获取此流运算后的最大值元素
Optional<T> min(Comparator< ? super T> comparator)获取此流运算后的最小值元素
//请计算出身高超过168的学生有几人
long size=students.stream().filter(s->s.getHeight()>168).count();


//请找出身高最高的学生对象,并输出
Student s=students.stream().max((o1, o2) -> Double.compare(o1.getHeight(),o2.getHeight() )).get();


//请找出身高最低的学生对象,并输出
Student s=students.stream().min((o1, o2) -> Double.compare(o1.getHeight(),o2.getHeight() )).get();

【1】收集Stream流

收集Stream流:就是把Stream流操作后的结果转回到集合或者数组中去返回

Stream流:方便操作集合/数组的手段;集合/数组:才是开发中的目的

流只能收集一次

Stream提供的常用终结方法说明
R collect(collector collector)把流处理后的结果收集到一个指定的集合中去
object[] toArray()把流处理后的结果收集到一个数组中去
//请找出身高超过170的学生对象,并放到一个新集合中去返回
List<Student>students1=students.stream().filter(a->a.getHeight()>170).collect(Collectors.toList());


Set<Student>students2=students.stream().filter(a->a.getHeight()>170).collect(Collectors.toSet());


//请找出身高超过170的学生对象,并把学生对象的名字和身高,存入到一个Map集合返回
Map<String,Double>map=students.stream().filter(a->a.getHeight()>170).distinct().collect(Collectors.toMap(a->a.getName(), a->a.getHeight()));
//distinct()去除重复对象

//请找出身高超过170的学生对象,并放到一个数组中去返回
Object[]arr=students.stream().filter(a->a.getHeight()>170).toArray();
Student[]arr=students.stream().filter(a->a.getHeight()>170).toArray(len->new Student[len]);
Collectors工具类提供了具体的收集方式说明
public static <T> collector toList()把元素收集到List集合中
public static <T> collector toSet()把元素收集到set集合中
public static collector toMap(Function keyMapper , Function valueMapper)把元素收集到Map集合中

  • 21
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值