Java基础进阶14天

本文详细介绍了Java基础知识,包括Object类、toString方法、equals方法和数据类型的比较。接着,讲解了Java集合框架,如ArrayList、LinkedList、HashSet、HashMap等的特性、遍历方式及操作方法。此外,提到了迭代器、增强for循环和泛型的使用,以及如何通过Stream流进行简化操作。最后,探讨了日志的重要性,展示了如何通过JUnit进行单元测试,并简述了反射和注解的概念。
摘要由CSDN通过智能技术生成

day1
lang包无需导包 。
object类:
java.lang.Object类是Java语言中根类,即所有类的父类,所有对象包括数组,都实现这个类的方法。
直接打印对象的地址值没有意义,需要重写object类中的toString方法打印对象的属性值。
看一个类是否重写了toString,直接打印这个类的对象即可,如果没有重写toString方法那么打印的是对象的地址值(ArrayList集合 和键盘录入Scanner 有tostring方法)。
equals方法
object类中equals方法,默认比较的是两个对象的地址值,没有意义,所以我们要重写equals方法,比较两个对象的属性。
基本数据类型:比较的是值。
引用数据类型:比较的是两个对象的地址值。
问题:方法里面隐含这一个多态。
多态的弊端:无法使用子类特有的内容(属性和方法)。
Object obj=p2=new Person(“你好”,909);
解决:可以使用向下转型(强转)把obj类型转换为person。
默认地址比较
如果没有覆盖重写equals方式,那么 Object类中默认进行==运算符的对象地址比较,只要不是同一个对象,结果必然为false.
对象内容比较
如果希望进行对象的内容比较,即所有或指定的部分成员变量相同就判断两个对象相同,则可以覆盖重写equals方法。

public class Demo10 {
   
    public static void main(String[] args) {
   
       String s1="abc";
       //String s1=null;
       String s2="abc";
        boolean b1 = s1.equals(s2);
        System.out.println(b1);//null是不能调用方法的,就会抛出空指针异常

        //Objects类的equals方法:对两个对象进行比较,防止空指针异常
        boolean b2 = Objects.equals(s1, s2);
        System.out.println(b2);//true
    }
}

Date类
util需要导包
在这里插入图片描述
有了构造方法可以创建对象,有了对象在使用其里面的成员方法
Date类的构造方法

 //Date类的空参数构造方法  date()获取当前系统的日期时间
    private static void demo1() {
   
        Date date = new Date();
        System.out.println(date);//Sat Jun 12 11:58:10 CST 2021
    }
    demo2();
    demo3();
}
//long getTime() 把日期转换为毫秒值,相当于System.currentTimeMillis()
private static void demo3() {
   
    Date date = new Date();
    long time = date.getTime();
    System.out.println(time);
}
//Date类的带参数构造方法
//Date(Long date):传递毫秒值,把毫秒值转换为Date日期
private static void demo2() {
   
    Date date = new Date(0L);
    System.out.println(date);
    Date date1 = new Date(1623488653350L);
    System.out.println(date1);
}

DateFormat类
DateFormat类是一个抽象类,无法直接创建对象使用,可以使用DateFormat类的子类 SimpleDateFormat
在这里插入图片描述
写对应的模式,会把模式替换成对应的日期和时间
“yyyy-MM-dd HH:mm:ss”
注意:模式中的字母不能更改,连接模式的符号可以改变
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
Calendar类
java.util.Calender类:日历类
Calendar类是一个抽象类,里边提供了很好操作日历字段的方法(YEAR,MONTH,DAY_OF_MONTH,HOUR)
Canlendar类无法直接创建对象使用,里边有一个静态方法叫getInstance(),该方法返回了Calender类的子类对象
static Calendar getInstance() 使用默认时区和语言环境获得一个日历

Calendar c=Calender.getInstance(); 多态
sout©;
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

private static void demo4() {
   
        //public Date getTime():返回一个表示此Calendar时间值,(从历元到现在的毫秒值偏移量)的date
        //对象,把日历对象转换为日期对象
        Calendar c = Calendar.getInstance();
        Date date = c.getTime();
        System.out.println(date);
    }

System类(系统类)
lang.System类中提供了大量的静态方法,可以获取与系统相关的信息或系统操作

public static long currenTimeMillis():返回以毫秒单位的当前时间
public static void arraycopy(Object src,int srcPos,Object dest,int desPos,int length):
将数组中指定的数据拷贝到另一个数组中

public class Demo10 {
   
    public static void main(String[] args) {
   
        long s = System.currentTimeMillis();
        for (int i = 0; i < 9999; i++) {
   
            System.out.println(i);
        }
        long e = System.currentTimeMillis();
        System.out.println(e-s);//69毫秒
    }
}

在这里插入图片描述
在这里插入图片描述
StringBuilder类
在这里插入图片描述
String类:字符串是常量,他们的值在创建之后不能更改,字符串的底层是一个final修饰的数组,不能改变,是一个常量。
private final byte[] value;
StringBuilder类:字符串缓冲区可以提高字符串的操作效率,看成一个长度可以变化的字符串,底层也是一个数组,但是没有被final修饰,可以改变长度。
byte[] value=new byte[16]

StringBuilder的构造方法
pubilc stringBuilder():构造一个空的StringBuilder容器
public stringBuilder(String str):构造一个StringBuilder容器,并将字符串添加进去

public class Demo2 {
   
    public static void main(String[] args) {
   
        StringBuffer sb1 = new StringBuffer();
        System.out.println(sb1);//(空白)
        StringBuffer sb2 = new StringBuffer("itcast");
        System.out.println(sb2);//itcast
    }
}

StringBuilder的常用方法:
public StringBuilder append(…):添加任意类型数据的字符串形式,并返回当前对象自身。
public String toString() :将当前StringBuilder对象转换为String对象。

public class DemoStringBuilder {
   
    public static void main(String[] args) {
   
        StringBuilder bu = new StringBuilder();
        //append方法返回的是this,调用方法的对象bu,this==bu
      StringBuilder bu1=  bu.append("abd");//把bu地址值赋给了bu2
        System.out.println(bu);//abd
        System.out.println(bu1);//abd
        System.out.println(bu==bu1);//true 比较的是地址值
        //使用append方法无需接收返回值
        bu.append(1);
        bu.append("abc");
        bu.append(8.5);
        bu.append('中');
        System.out.println(bu);
        //链式编程:方法返回值是一个对象,可以继续调用方法
        bu.append("abc").append(23).append(8.5).append('中');
        System.out.println(bu);
    }
}

StringBuilder和String可以相互转换:
String->StringBuilder:可以使用StringBuilder的构造方法。
StringBuilder(string str)构造一个字符串生成器,并初始化指定的字符串内容。
StringBuilder->String:可以使用StringBuilder中的toString方法。
public string toString():将当前stringBuilder对象转换为String对象。

public class DemoStringBuilder {
   
    public static void main(String[] args) {
   
        //String->StringBuilder
        String str="hello";
        System.out.println("str"+str);
        StringBuilder bu = new StringBuilder();
        bu.append("worle");
        System.out.println(bu);
        //StringBuilder->String
        String s = bu.toString();
        System.out.println(s);
    }
}

包装类
在这里插入图片描述
包装类
基本数据类型,使用起来非常方便,但是没有对应的方法操作这些基本类型的数据可以使用一个类,把基本类型的数据装起来,在类中定义一些方法,这个类叫做包装类我们可以使用类中的方法操作这些基本类型的数据.


拆箱和装箱
基本类型与对应的包装类对象之间,来回转换的过程称为装相和拆箱.
装箱:从基本类型转换为对应的包装类对象.
拆箱:冲包装类对象转换为对应的基本类型.

装箱:把基本类型的数据,包装到包装类中(基本类型的数据—>包装类).
构造方法:
integer(int value)构造一个新分配的Integer对象,它表示指定的int值.
integer(String s)构造一个新分配的Integer对象,它表示String参数所指示的int值.
传递的字符串,必须是基本类型的字符串,否则会抛出异常 100 正确 0 抛异常
静态方法:
static Integer valueOf(int i)返回一个表示指定的int 值的Integer实例.
static Integer valueOf(String s)返回保存指定的string 的值的Integer 对象.
拆箱:在包装类中取出基本类型的数据(包装类---->基本类型的数据).
成员方法:
int intValue() 以int 类型返回该Integer 的值.

在这里插入图片描述
在这里插入图片描述
基本类型与字符串类型之间的相互转换
基本类型->字符串(String)
1.基本类型的值,“”最简单的方法(工作中常用)
2.包装类的静态方法toString(参数),不是Object类的toString() 重载
static string toString(int i) 返回一个表示指定整数的String 对象
3.String类的静态方法valueOf(参数)
static String valueOf(int i)返回 int 参数 的字符串表示形式
字符串(String)->基本类型
使用包装类的静态方法parseXXX(“字符串”);
Integer类:static int parseInt(String s)
Double类:static double parseDouble(String s)

public class Demo2 {
   
    public static void main(String[] args) {
   
        //基本类型->字符串(String)
        int li=100;
        String s1=li+"";
        System.out.println(s1+200);

        String S2 = Integer.toString(100);
        System.out.println(S2+200);//100200

        String s3 = String.valueOf(100);
        System.out.println(s3+200);//100200

        //字符串(String)->基本类型
        int i=Integer.parseInt(s1);
        System.out.println(i-10);//90

        int a = Integer.parseInt("a");
        System.out.println(a);//NumberFormatException
    }
}

day2
变量是为了存储数据
Collection集合
/集合存储字符串对象包装类 ArrayList
集合和数组的区别?
数组的长度是固定的,集合的长度是可变的
数组中存储的是同一类型的元素,可以存储基本数据类型,集合存储的都是对象,而且对象的类型可以不一致,在开发中一般当对象多的时候,使用集合进行存储。
在这里插入图片描述
Collection接口:所有单列集合的最顶层的接口,里边定义了所有单列集合共性的方法,任意的单列
集合都可以使用collection接口中的方法。

共性的方法如下:
public boolean add(E e):把给定的对象添加到当前集合中.
public boolean clear():清空集合中所有的元素(clear:清楚集合中所有的元素,但是不删除集合,集合还存在).
public boolean remove (E e):把给定的对象在当前集合中删除.
public boolean contains(E e):判断当前集合中是否包含给定的对象.
public boolean isEmpty():判断当前集合是否为空.
public int size():返回集合中元素的个数.
public object[] toArrays():把集合中的元素,存储都数组中.

collection集合中没有索引,不能使用普通遍历遍历,使用:Iterator迭代器

在程序中经常要遍历集合中所有的元素,而Itertor主要用于迭代访问即遍历
迭代:即collection集合元素的通用获取方式,在取元素之前先要判断集合中有没有元素,如果有就把这个元素取出来,继续在判断,如果还有就在取出来,一直把集合中的所有元素全部取出来。

itertor接口的常用方法如下:
public E next :返回迭代的下一个元素 取出集合的下一个元素
public boolean hasNext(): 如果仍有元素可以迭代,则返回true 判断集合中还有没有下一个元素有就返回true,没有就返回false
Iterator迭代器,是一个接口,我们无法直接使用,需要使用Iterator接口实现类对象,获取实现类的方式比较特殊。

Collection 接口中有一个方法,叫iterator()----->这个方法返回的就是迭代器的实现类对象,Iterator iterator() 返回在此 collection 的元素上进行的迭代器。

迭代器的使用步骤
1 使用集合中的方法iterator()获取迭代器的实现类对象,使用步骤:
1.使用集合中的方法itertor()获取迭代器的实现类对象,使用Iterator接口接收(多态)
2.使用Iterator接口中的方法hasNext判断还有没有下一个元素
3.使用Iterator接口中的方法next取出集合中的下一个元素
注意:Iterator接口也是有泛型的,迭代器的泛型跟着集合走,集合什么泛型,迭代器就是什么泛型

public class Demo88 {
   
    public static void main(String[] args) {
   
       Collection<String> coll=new ArrayList<>();
       coll.add("kebi");
       coll.add("kebi3");
       coll.add("kebi2");
       //  多态          接口          实现类对象
        Iterator<String> iterator = coll.iterator();
        while (iterator.hasNext()){
   
            String next = iterator.next();
            System.out.println(next);
        }
    }
}

错误:NoSuchElementException 集合中没有元素会出现false 第二次时就会报错
在这里插入图片描述
增强for循环
它的内部原理其实是个iterator迭代器,所以在遍历的过程中,不能对集合中的元素进行增删操作
for(集合或者数组数据类型 变量 :collection集合或者数组){iter
写操作代码
}
注意增强for循环必须有被遍历的目标,目标只能是collection或者数组

泛型概念
在前面学习集合时,我们都知道集合中时可以存放任意对象的,只能把对象存储集合后,那么这时他们都会被提升成Object类型。当
我们在取出每一个对象,并且进行相应的操作,
在这里插入图片描述
创建集合对象,使用泛型
好处:
1.避免了类型转换的麻烦,存储的是什么类型,取出的就是什么类型
2.把运行期异常(代码运行之后会抛出的异常),提升到了编译期(写代码的时候会报错)
弊端:泛型是什么类型,只能存储什么类型的数据
创建集合对象,不使用泛型
好处:集合不使用泛型,默认的类型就是Object类型,可以 存储任意的数据
弊端:不安全,会引发异常

定义和使用含有泛型的类
定义格式:
修饰符 class 类名<代表泛型的变量>{}
例如: ArrayList集合:

    class ArrayList<E>{
   
        public boolean add(E e){
   
            return true;
        }
        public E get(int index){
    }
}

案例如下:

/*
* 定义一个含有泛型的类,模拟ArrayList集合
* 泛型是一个未知的数据类型,可以使用Integer,String,Student....
* 创建对象的时候确认泛型的数据类型
* */
public class GenericClass<E> {
   
    private E name;

    public E getName() {
   
        return name;
    }
    public void setName(E name) {
   
        this.name = name;
    }
}
public class Demo1GenericClass {
   
    public static void main(String[] args) {
   
        //不写泛型默认为Objec类型
        GenericClass<Object> gc = new GenericClass<>();
        gc.setName("只能是字符串");
        Object obj = gc.getName();
        System.out.println(obj);
        //创建GenericClass,泛型使用Iteger类型
        GenericClass<Integer> gc2 = new GenericClass<>();
        gc2.setName(1);
        Integer name = gc2.getName();
        System.out.println(name);
        //创建GenericClass,泛型使用String类型
        GenericClass<String> gc3 = new GenericClass<>();
        gc3.setName("小明");
        String name1 = gc3.getName();
        System.out.println(name1);
    }
}

含有泛型的方法
定义格式:
修饰符<代表泛型的变量> 返回值类型 方法名(参数){}
例如:

public class Demo3 {
   
    public <MVP>void show( MVP mvp){
   
        System.out.println(mvp.getClass());
    }
    public <MVP> MVP show2(MVP mvp){
   
        return mvp;
    }
}

使用格式:调用方法时,确认泛型的类型
含有泛型的方法,在调用方法的时候确定泛型的数据类型
传递什么类型的参数,泛型就是什么类型

public class GenericMethod {
   
    //定义一个含有泛型的方法
    public <M> void method01(M m){
   
        System.out.println(m);
    }
    //定义一个含有泛型的静态方法
    public static <S> void method02(S s){
   
        System.out.println(s);
    }
}

静态方法,通过类名 方法名(参数)可以直接使用
下面是调用:

public class Demo3GenericMethod {
   
    public static void main(String[] args) {
   
        //创建Genericmethod对象
        GenericMethod gm = new GenericMethod();
        gm.method01(10);
        gm.method01("abc");
        gm.method01(8.8);
        gm.method01(true);
        gm.method02("静态方法,不建议创建对象使用");
        
        //静态方法,通过类名,方法名(参数)可以直接使用
        GenericMethod.method02("静态方法");
        GenericMethod.method02(1);
    }
}

含有泛型的接口
定义格式
修饰符 interface接口名<代表泛型的变量>{}
例如:

public interface MyGenericInterface <E>{
   
    public abstract void add(E e);
    
    public  abstract E getE();
}

例:

/*
定义含有泛型的接口
* */
public interface GenericInterface <I>{
   
    public abstract void method(I i);
}

实现类:

/*
含有泛型的接口,第一种使用方式:定义接口的实现类,实现接口,指定接口的泛型
public interface Iterator<E>{
    E  next();
}
Scanner类实现了Iterator接口,并指定接口的泛型为String,所以重写next方法泛型默认就是String
public final class Scanner implements Iterator<String>{
public string next(){}
}
* */

public class GenericInterfaceImpl1 implements GenericInterface<String>{
   
    @Override
    public void method(String s) {
   
        System.out.println(s);
    }
}

测试类:

public class Demo4GenericInterface {
   
    public static void main(String[] args) {
   
        //测试含有泛型的接口
        GenericInterfaceImpl1 gi1 = new GenericInterfaceImpl1();
        gi1.method("字符串");
    }
}

含有泛型的接口,第二种使用方式:

/*
含有泛型的接口,第二种使用方式:接口使用什么泛型,实现类就使用什么泛型,类跟着接口走
就相当于定义了一个含有泛型的类,创建对象的时候确定泛型的类型
public interface List<E>{
boolean add(E e);
E get(int index);
}
public class ArrayList<E> implements list<E>{
 public boolean add(E e){}
 public E get(int index) 
}

}
* */
public class GenericInterfaceImpl2<I> implements GenericInterface<I>{
   
    @Override
    public void method(I i) {
   
        System.out.println(i);
    }
}

含有泛型的接口,第二种使用方式的测试类:

public class Demo4GenericInterface {
   
    public static void main(String[] args) {
   
        //测试含有泛型的接口
        GenericInterfaceImpl1 gi1 = new GenericInterfaceImpl1();
        gi1.method("字符串");
        //创建GenericInterfaceImpl2对象
        GenericInterfaceImpl2<Double> gi2 = new GenericInterfaceImpl2<Double>();
        gi2.method(8.8);
        GenericInterfaceImpl2<Integer> gi3 = new GenericInterfaceImpl2<Integer>();
        gi3.method(11);
    }
}

泛型的通配符
? 代表任意的数据类型
使用方式:不能创建对象始用,只能作为方法的参数使用
增强for 没有索引,所以使用普通的for循环

day3
数据结构
下面有关的是跟集合有关的数据结构
数据存储的常用结构有:栈 队列 数组 链表 红黑树

栈:
先进后出
在这里插入图片描述

队列:
先进先出
在这里插入图片描述
数组:
查询快:数组的地址是连续的,我们通过数组的首地址可以找到数组,通过数组的索引可以快速查找某个元素。
增删慢:数组的长度是固定的我们想要增删一个元素必须创建一个新数组,把原数组的数据复制过来
在这里插入图片描述
链表结构:
查询慢:链表中地址不是连续的,每次查询元素,都必须从头开始查询
增删快:链表结构增删一个元素,对链表的整体结构没有影响,所以增删快
在这里插入图片描述
红黑树:
特点趋近于平衡树,查询的速度非常的快,查询叶子节点最大次数和最小次数不能超过2倍
树型结构:
在这里插入图片描述
不是地址值说明重写了toString方法
List接口
1 有序的集合,存储元素和取出元素的顺序是一致的
2 有索引 包含了一些带索引的方法
3 允许存储重复的元素

List接口中带索引的方法 特有如下
public void add(int index,E element):将制定的元素,添加到该集合中的指定位置上
public E get(int index):返回集合中的指定的位置的元素
public E remove(int index):移除列表中指定的位置的元素,返回的是被移除的元素、
public E set(int index ,E element):用指定的元素替换集合中指定位置的元素,返回值的更新前的元素
注意:操作索引的时候,一定要防止索引越界异常

public class Demo4 {
   
    public static void main(String[] args) {
   
        List<String> list = new ArrayList<>();
        list.add("a");
        list.add("b");
        list.add("c");
        //System.out.println(list);//不是地址值,重写了toString方法
        list.add(3,"dddd");
        System.out.println(list);
        list.remove(3);
        System.out.println(list);
        list.set(1,"B");
        System.out.println(list);
        //遍历集合
        for (int i = 0; i < list.size(); i++) {
   
            String s = list.get(i);
            System.out.println(s);
        }
        //增强for循环 使用Iterator 遍历
        Iterator<String> iterator = list.iterator();
        while (iterator.hasNext()){
   
            String next = iterator.next();
            System.out.println(next);
        }
        for (String s : list) {
   
            System.out.println(s);
        }
    }
}

List集合的子类
ArrayList集合:集合数据存储的结构是数组结构,元素增删慢,查询快,优于日常开发中使用最多的功能为查询数组,遍历数据,所以ArrayList是最常用的集合.
LinkedList集合:集合数据存储的结构是链表结构,方便元素添加,删除的集合
LinkedList是一个双向链表。是list接口的实现类
注意:使用LinkedList集合特有的方法,不能使用多态(看不到子类中特有的方法)
在这里插入图片描述
Set接口
接口特点:set中的方法跟collection方法是一致的 extends collection接口
1 不允许存储重复的元素
2 没有索引,没有带索引的方法,也不能使用普通的for循环遍历
3 是一个无序的集合,存储元素和取出元素的顺序有可能不一致
4 底层是一个哈希表结构,查询的速度非常快

public class Person extends Object{
   
    //重写hashCode方法
    @Override
    public int hashCode(){
   
        return 1;
    }
}
public class Demo4 {
   
    public static void main(String[] args) {
   
        Set<Integer> set=new HashSet<>();
        set.add(1);
        set.add(2);
        set.add(3);
        //使用迭代器和增强for
        Iterator<Integer> iterator = set.iterator();
        while (iterator.hasNext()){
   
            Integer next = iterator.next();
            System.out.println(next);
        }
        for (Integer integer : set) {
   
            System.out.println(integer);
        }
    }
}

哈希值:是一个十进制的整数,由系统随机给出(就是对象的地址值,是一个逻辑地址,是模拟出来得到地址,不是数据实际存储的物理地址)。
在Objec类有一个方法,可以获取对象的哈希值就是—>int hashCode():返回该对象的哈希码值。
hashCode方法的源码:
public native int hashCode();
native:代表该方法调用的是本地操作系统的方法

public class Demo1HashCode {
   
    public static void main(String[] args) {
   
        //Person类继承了Object类,所以可以使用Object类的hashCode方法
        Person P1 = new Person();
        int h1 = P1.hashCode();
        System.out.println(h1);//460141958

        Person P2 = new Person();
        int h2 = P2.hashCode();
        System.out.println(h2);//1163157884
        /*
        toString方法源码:
        return getClass.getName()+"@"+Integet.toHexString(hashCode());
        */
        System.out.println(P1);//com.it.heima.Person@1b6d3586
        System.out.println(P2);//com.it.heima.Person@4554617c
        System.out.println(P1=P2);//false

        /*
        String 类的哈希值  String类重写Object类的hashCode方法
        */
        String s1=new String("abc");
        String s2=new String("abc");
        System.out.println(s1.hashCode());//96354
        System.out.println(s2.hashCode());//96354
        System.out.println("重地");
    }
}

哈希表:
特点:查询速度快
在这里插入图片描述
为什么set集合元素不能重复?
Set集合在调用add方法的时候,add方法调用元素的hashCode和equals方法,判断元素是否重复。
在这里插入图片描述
HashSet存储自定义类型元素?
set集合元素唯一的要求是:必须重写hashCode方法和equals方法
重写toString方法是为了输出的时候不是地址值!
没有用set集合就不用添加hashCode和equals方法,添加这两个方法确定元素的唯一性

LinkedHashSet集合
LinkedHashSet集合继承(extends) HashSet集合
特点:底层是一个哈希表(数组加链表/红黑树)+链表:多了一条链表(记录元素的存储顺序),保证元素有序。

public class DemoLinkedHashSet {
   
    public static void main(String[] args) {
   
        HashSet<String> set = new HashSet<>();
        set.add("www");
        set.add("ccc");
        set.add("dddd");
        set.add("aaa");
        System.out.println(set);//无序 ,不允许重复
        LinkedHashSet<String>linked=new LinkedHashSet<>();
        linked.add("sss");
        linked.add("sss");
        linked.add("ssssdd");
        linked.add("abc");
        System.out.println(linked);//有序,不允许重复
    }
}

可变参数
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
Collections集合工具类,用来对集合进行操作
可以直接使用(因为是静态方法 可以通过类名和方法名调用)。
常用功能如下:
java.utils.collections 是集合工具类,用来对集合进行操作.
public static boolean addAll(collectionc,T…elements):往集合中添加一些元素.
public static void shuffle(List<?> list)打乱顺序,打乱集合顺序.
public static void sort(List<?>list):将集合中元素按照默认规则排序.
public static void sort(List list.Comparator<? super T>):将集合中元素按照指定规则排序.

public class Demo1Collections {
   
    public static void main(String[] args) {
   
        ArrayList<String> list = new ArrayList<>();
        Collections.addAll(list,"a","b","c","d");
        System.out.println(list);
        
        Collections.shuffle(list);
        System.out.println(list);
    }
}

java.utils.Collections是集合工具类,用来对集合进行操作,部分方法如下:

public static void sort(list list):将集合中元素按照默认规则排序。
注意:
sort(list list)使用前提
被排序的集合里边存储的元素,必须实现Comparable,重写接口中的方法compareTo定义排序的规则。
Comparable接口的排序规则:
自己(this)–参数:升序

public class Person1 implements Comparable<Person1>{
   
    private int age;
    private String name;

    public Person1() {
   
    }
    public Person1(int age, String name) {
   
        this.age = age;
        this.name = name;
    }
    public int getAge() {
   
        return age;
    }
    public void setAge(int age) {
   
        this.age = age;
    }
    public String getName() {
   
        return name;
    }
    public void setName(String name) {
   
        this.name = name;
    }
    @Override
    public String toString() {
   
        return "Person1{" +
                "age=" + age +
                ", name='" + name + '\'' +
                '}';
    }
    @Override
    public int compareTo(Person1 o) {
   
        return this.getAge()-o.getAge();
    }
}

测试:

public class Demo5 {
   
    public static void main(String[] args) {
   
        ArrayList<Person1>arrayList=new ArrayList<>();
        arrayList.add(new Person1(215,"你好"));
        arrayList.add(new Person1(213,"你好"));
        arrayList.add(new Person1(214,"你好"));
        Collections.sort(arrayList);
        System.out.println(arrayList);
    }
}

Comparator和Comparable的区别:

/*
java.utils.Collections是集合工具类,用来对集合进行操作,部分方法如下:
public static <T> void sort(List<T> list.Comparator<? super T>):将集合中元素按照指定规则排序
Comparator和Comparable的区别
    Comparable:自己和别人比较,自己需要实现Comparable接口,重写比较的规则compareTo方法
    Compartor:相当于找一个第三方的裁判,比较两个

    Comparator的排序规则:
     o1-o2:升序
*/
public class Demo6Sort {
   
    public static void main(String[] args) {
   
        ArrayList<Integer> list01=new ArrayList<>();
        list01.add(3);
        list01.add(2);
        list01.add(1);
        System.out.println(list01);
        Collections.sort(list01, new Comparator<Integer>() {
   
            @Override
            public int compare(Integer o1, Integer o2) {
   
               // return o1-o2;//升序
                return o2-o1;//降序
            }
        });
        ArrayList<Student> list02=new ArrayList<>();
        list02.add(new Student("科比",24));
        list02.add(new Student("詹姆斯",23));
        list02.add(new Student("杜兰",22));
        /*Collections.sort(list02, new Comparator<Student>() {
            @Override
            public int compare(Student o1, Student o2) {
                return o1.getAge()- o2.getAge();
            }
        });*/
        Collections.sort(list02, new Comparator<Student>() {
   
            @Override
            public int compare(Student o1,Student o2) {
   
                //按照年龄升序排列
               int result= o1.getAge()- o2.getAge();
                //如果两人年龄相同,在使用姓名的第一个字比较
                if (result==0){
   
                    result =o1.getName().charAt(0)-o2.getName().charAt(0);
                }
                    return result;
            }
        });
    }
}

day4------->Map<K,V>集合
1 Map集合是一个双列集合,一个元素包含了两个值,一个是key 一个是value.
2 Map集合中的元素,key和value的数据类型可以相同,也可以不同.
3 Map集合中的元素,key是不允许重复的,value是可以重复的.
4 Map集合中的元素,key和value是一一对应.

不同步就是多线程非常快.
Map的子类
java.util.Map<k,v>集合
Map集合的特点:
1.Map集合是一个双列结合,一个元素包含两个值,一个key,一个value
2.Map集合中的元素,key和vaule的数据类型可以相同,也可以不同
3.Map集合中的元素,key是不允许重复的,value是可以重复的
4.Map集合中的元素,key和value是一 一对应
java.util.HashMap<k,v>集合 implements Map<k,v>接口
hashmap集合的特点:
1.HashMap集底层是哈希表:查询的速度特别的快
jdk1.8之前:数组+单向链表
jdk1.8之后:数组+单向链/红黑树(链表的长度超过8):提高查询的速度
3.Hashmap集合是一个无序集合 存储元素和去除元素的顺序可能不一样
java.util.LinkedHashMap<k,v>集合 extendsHashMap<k,v>集合
LinkedHashMap的特点:
1.LinkedHashMap集合底层是哈希表+链表(保证迭代的顺序)
2.LinkedHashMap集合是一个有序集合,存储元素和取出元素的顺序是一致的。

Map接口中定义了很多方法 常用如下:
public V remove(Object key):把指定的键 所对应的键值对元素 在Map集合中删除返回被删除元素的值.
public V put(k key, V value):把指定的键与指定的值添加到Map集合中.
public V get(Object key)根据指定的键 在Map集合中获取对应的值.
boolean containsKey(Object key)判断集合中是否包含指定的键.
public Set keySet():获取Map集合中所以的键 存储到Set集合中.
public Set<Map.EntryentrySet>:获取到Map集合中所有的键值对对象的集合(Set集合).

public class DemoMap {
   
    public static void main(String[] args) {
   
        show01();
    }
    /*
    public V remove(Object key):把指定的键,所对应的键值对元素,在Map集合中删除,返回被删除的元素的值
    返回值: V
      key存在,v返回被删除的值
      key不存在,v返回null
    */
    private static void show01() {
   
        Map<String,String> map=new HashMap<>();
        String v1 = map.put("李晨", "邓超");
        System.out.println("v1"+v1);//v1null
        String v2 = map.put("李晨", "邓超");
        System.out.println("v2"+v2);//v2邓超
        System.out.println(map);//{李晨=邓超}
        }
    }
//public V remove(Object key):把指定的键,所对应的键值对元素,在Map集合中删除,返回被删除元素的值
    //返回值:V
    // Key 存在,v返回被删除的值
    //key不存在,v返回null
    private static void show02() {
   
        Map<String,Integer> map=new HashMap<>();
        map.put("科比",24);
        map.put("詹姆斯",23);
        map.put("欧文",8);
        map.put("哈登",16);
        System.out.println(map);
        Integer v1 = map.remove("科比");
        System.out.println(v1);

        System.out.println(map);
        Integer v2 = map.remove("科比1");
        System.out.println(v2);//v2:null
    }

通过键找值的方式遍历Map集合
在这里插入图片描述
Map集合的第一种遍历方式:通过键找值方式:
Map集合中的方法:
Set keySet(): 返回此映射中包含的键的 Set视图,
实现步骤
1.使用map集合中方法keySet(),把Map集合所有的key取出来,存储到一个Set集合中。
2.遍历set集合,获取map集合中的每一个key.
3.通过map集合中的方法get(key),通过key找到value.

 public static void main(String[] args) {
   
        Map<String,Integer> map=new HashMap<>();
        map.put("nihoa",23);
        map.put("nihdoa",233);
        map.put("nihddoa",2333);
        map.put("nihddoa",2333);
        Set<String> keySet = map.keySet();
        Iterator<String> iterator = keySet.iterator();
        while (iterator.hasNext()){
   
            String key= iterator.next();
            Integer value = map.get(key);
            System.out.println(key+","+value);
        }
        for (String s : keySet) {
   
            Integer values = map.get(s);
            System.out.println(s+"="+values);
        }
    }

Entry键值对对象
嵌套类又称为内部类
Map.Entry<K,V>:在Map接口中有一个内部接口Entry
作用:当Map集合一创建,那么就会在Map集合中创建一个Entry对象,用来记录键与值(键值对对象,键与值的映射关系)–结婚证
在这里插入图片描述
Map集合遍历的第二种方式:使用Entry对象遍历
Map集合中的方法:
Set<Map.Entry<K,V>> entrySet() 返回此映射包含的映射关系的Set视图.
实现步骤:
1 使用Map集合中的方法entrySet(),把Map集合中多个Entry对象取出来,存储到一个Set集合中.
2 遍历Set集合,获取每一个Entry对象.
3 使用Entry对象的方法getKey()和getValue()获取键与值.

 private static void show02() {
   
        //创建Map集合
        Map<String,Integer> map=new HashMap<>();
        map.put("科比",24);
        map.put("詹姆斯",23);
        map.put("欧文",8);
        map.put("哈登",16);
       //第一步
        Set<Map.Entry<String, Integer>> set = map.entrySet();
        Iterator<Map.Entry<String, Integer>> it = set.iterator();
        while (it.hasNext()){
   
            Map.Entry<String, Integer> entry = it.next();
            String key = entry.getKey();
            Integer value = entry.getValue();
            System.out.println(key+value);
        }
    }

HaspMap存储自定义类型键值
map集合保证key是唯一的:
作为key的元素,必须重写hashCode方法和equals方法,比保证key唯一.

/*
    HashMap存储自定义类型键值
    key:String 类型
        String类重写hashCode方法和equals方法,可以保证key唯一
    value:Student类型
          value 可以重复(同名同年龄的人视为同一个)
    */
    private static void show01() {
   
        Map<String,Student>map=new HashMap<>();
        map.put("北京",new Student("张三",46));
        map.put("上海",new Student("李四",56));
        map.put("广东",new Student("王五",66));
        Set<String> set = map.keySet();
        for (String key : set) {
   
            Student value = map.get(key);
            System.out.println(key+value);
        }
    }

/*
    HashMap存储自定义类型键值
    key:Student 类型
        Student类重写hashCode方法和equals方法,可以保证key唯一
    value:String类型
            可以重复
    */
    private static void show03() {
   
        Map<Student,String>map=new HashMap<>();
        map.put(new Student("张三",86),"上海");
        map.put(new Student("李四",46),"北京");
        map.put(new Student("王五",96),"广东");
        Set<Map.Entry<Student, String>> set = map.entrySet();
        for (Map.Entry<Student, String> entry : set) {
   
            String value = entry.getValue();
            Student key = entry.getKey();
            System.out.println(value+key);
        }
    }

LinkedHashMap是HashMap的子类

/*
    java.util.LinkedHashMap<K,v> entends HashMap<K,V>
    Map 接口的哈希表和链表列表实现,具体可预知的迭代顺序
    底层原理:
       哈希表+链表(记录元素的顺序)
*/
public class Demo01LinkedHashMap {
   
    public static void main(String[] args) {
   
        HashMap<String,String>map=new HashMap<>();
        map.put("a","a");
        map.put("c","c");
        map.put("a","d");
        map.put("b","b");

        System.out.println(map);
        LinkedHashMap<String,String>linked=new LinkedHashMap<>();
        linked.put("c","c");
        linked.put("a","a");
        linked.put("b","b");
        linked.put("a","d");
        System.out.println(map);
    }
}

同步就是单线程 速度慢
在这里插入图片描述
java.util.Hashtable<K,V>集合 implement Map<K,v>接口
Hastable:底层也是一个哈希表,是一个线程安全的集合,是单线程集合,速度慢。
hashMap:底层是个哈希表,是一个线程不安全的集合,是多线程的集合,速度快。
HashMap集合:可以存储null值,null键
Hashtable集合,不能存储null值,null键
Hastable的子类properties集合是个一唯一和IO流相结合的集合。

public class Demo2Hashtable {
   
    public static void main(String[] args) {
   
        HashMap<String,String>map=new HashMap<>();
        map.put(null,"a");
        map.put("b",null);
        map.put(null,null);
        System.out.println(map);//{null=null, b=null}
        Hashtable<String,String>table=new Hashtable<>();
        
        table.put(null,null);//NullPointerException
        table.put("a",null);//NullPointerException
        table.put(null,"b");//NullPointerException
    }
    
}

判断输入的字符串有几个案例下:

public class Demo99 {
   
    public static void main(String[] args) {
   
        //1.使用Scanner获取用户输入的字符串
        Scanner sc = new Scanner(System.in);
        System.out.println("请输入一个字串符");
        String str = sc.next();
        //2.创建Map集合,key是字符串中的字符,value是字符的个数
        HashMap<Character, Integer> map = new HashMap<>();
        //3.遍历字符串,获取每一个字符
        for (char c : str.toCharArray()) {
   
            //4.使用获取到的字符,去map集合判断key是否存在
            if (map.containsKey(c)){
   
                //key存在
                Integer value = map.get(c);
                value++;
                map.put(c,value);
            }else {
   
                //key不存在
                map.put(c,1);
            }
        }
        //5.遍历map集合,输出结果
        for (Character key : map.keySet()) {
   
            Integer value = map.get(key);
            System.out.println(key+"="+value);
        }
    }
}

遍历字符串,获取每一个字符
1.String类的方法toCharArray,把字符串转换为一个字符数组,遍历数据
2.String类的方法length()+charAt(索引)

在这里插入图片描述
在这里插入图片描述
Debug追踪,Debug调试程序:
特点:可以让代码逐行执行,查看代码执行的过程,调试程序中出现的bug。
使用方式:在行号的右边,鼠标左键单击,添加断点(每个方法的第一行,哪里有bug添加到哪里)右键,选择Debug执行程序,程序就会停留在添加的第一个断电处。
执行程序:
f8:逐行执行程序。
f7:进入到方法中。
shift+f8:跳出方法。
f9:跳到下一个断电,如果没有下一个断电,那么就结束程序。
ctrl+f2:退出debug模式 停止程序。
console:切换到控制台。

斗地主升级案例
在这里插入图片描述

public class Demo888 {
   
    public static void main(String[] args) {
   
        //1.准备牌,创建一个map集合,存储牌的索引和组装好的牌
        HashMap<Integer,String>poker=new HashMap<>();
        //创建一个list集合,存储牌的索引
        ArrayList
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值