Java学习日志

目录

目录

Java的数据类型

基本数据类型

引用数据类型

面向对象

封装

private关键字

继承

使用super调用父类中重写的方法、访问父类中被隐藏的字段

多态

 组合

初始化快

 抽象类:

接口:

  集合

Collection

ArrayList

LinkedList

Map  

泛型 

常见修饰符学习:半成品


因为前面几天Java学的很烂,进了项目组后就不能再像之前那样没有目的的去学Java了;

首先了解一下Java的运行机制,Java是一种混合型的编译运行方式,它在执行代码时是首先把Java文件整体的编译为class文件 这个class文件也叫做字节码文件,然后再按行去交给设备去运行,在运行的时候也不是直接运行在系统中的,而是运行在虚拟机中(JVM),Java语言的跨平台实际上是通过虚拟机实现的;

Java学习日志_第1张图片

JDK:Java的开发工具包,里面包含JVM虚拟机,核心类库,开发工具;

JRE:Java的运行环境;里面包含JVM,核心类库,运行工具;

JVM:Java虚拟机,真正运行Java程序的地方;

三者关系:JDK包含了JRE,JRE包含了JVM;

Java的数据类型

Java的数据类型分为两种,一种是基本数据类型,还有一种是引用数据类型 ;

基本数据类型

基本数据类型有八个,分别是:type,short,int,long,char,float,double,boolean;

引用数据类型

类、 接口类型、 数组类型、 枚举类型、 注解类型、 字符串型,例:String类型就是引用类型。

面向对象

理解面向对象,首先要了解类和对象;对象是面对对象方法中最基本的概念,是类的实例;类是具有共同属性,共同方法的一类事物。类是对象的抽象,对象是类的实例,并且类是整个软件系统最小的程序单元;

了解了类和对象,那我们要如何才能建立一个类呢;

Java语言里面定义类的简单语法如下:

[修饰符] class 类名
{
    构造器定义;;
    成员变量定义;
    方法定义;
}

 修饰符可以是public,final,abstract;类的修饰符到时候再具体讲;

 在IDEA中;

Java学习日志_第2张图片

 建好类后,Java学习日志_第3张图片

一个类里面包三个最常见的成员:构造器,成员变量和方法,类之间成员的定义顺序没有任何影响,各成员之间可以相互调用,但是要注意的是,static修饰的成员不能访问没有static修饰的成员。

构造器:构造器是一个类创建对象的根本途径,如果一个类没有构造器,Java会为该类提供一个默认的构造器,但是如果你自己在类中写了构造器,那么默认的构造器也就没了;值得注意的是,在定义构造器时不能用void声明;倘若你使用了void来声明,那么Java就会把这个所谓的构造器当成方法来处理,还要注意,构造器名一定要和类名相同;

Java学习日志_第4张图片

 创建完类后,如何创建对象呢;

Java学习日志_第5张图片

使用new在堆内存中开辟一段空间,用来存储对象的属性;Java学习日志_第6张图片

 加载对象时,方法会被加载到栈内存中进行调用;

方法的重载

方法重载是指在一个类中定义多个同名的方法,但要求每个方法具有不同的参数的类型或参数的个数,方法重载的前提是方法的名字要相同;我找了一个比较详细的博客,放在下面了;​​​​​方法的重载

 方法的重载

封装

封装是面向对象的三大特征之一,用白话理解,就是将东西放在一个箱子里面,只留下一个很小的口,只能通过特定的方法来使用里面的东西;

封装的原则:

将类的某些信息隐藏在类内部,不允许外部程序直接访问,而是通过该类提供的方法来实现对隐藏信息的操作和访问;例如成员变量private,提供对应的get()和set()方法;

封装的好处:

通过方法来控制成员变量的操作,提高了代码的安全性

把代码用方法进行封装,提高代码的复用性。

public class student {
    private String name;
    private int age;
    private String xh;
    public void setName(String name) {
        this.name=name;
    }
    public String getName(){
        return this.name;
    }
    public void setAge(int age){
        this.age=age;
    }
    public int getAge(){
        return this.age;
    }

    public void setXh(String xh) {
        this.xh = xh;
    }

    public String getXh() {
        return xh;
    }

    public student(){

    }
    public student(String name,int age,String xh){
        this.name=name;
        this.age=age;
        this.xh=xh;
    }
    public void stady(String xk){
        System.out.println(this.name+"正在学习"+xk);
    }
}

这就是一个我写的类,里面的成员变量使用private修饰;

private关键字

private:私有的;

作用:被private修饰的内容只能在本类中使用,其他类不能直接使用,但是其他类要是想访问这些内容,就要通过类所提供的访问方式,一般有两种访问方式;

1、设置器 setter : 为私有属性设置值

2、访问器 getter : 获取私有属性

  成员变量和局部变量

成员变量是在类里面定义的变量,局部变量是在方法里面定义的变量;

成员变量又分为实例变量和类变量,用static修饰的就是类变量,不用static修饰的变量就是实例变量;

与成员变量不同的是,局部变量必须初始化之后才能访问它,不然就会出错;、

包(package) 是组织类的一种方式,使用包的主要目的是保证类的唯一性.例如:你在代码中写了一个 Test 类. 然后你的舍友也可能写一个 Test 类. 如果出现两个同名的类, 就会冲突, 导致代码不能编译通过。

Java已经帮我们提供了很多现成的类供我们使用,我们在调用他们的时候使用import语句来导入包;

Java学习日志_第7张图片

使用 import static 可以导入包中的静态的方法和字段.

将类放到包中

基本规则:在文件的最上方加上一个 package 语句指定该代码在哪个包中
包名需要尽量指定成唯一的名字, 通常会用域名的颠倒形式(例如 com.bit.demo1 ).
包名要和代码路径相匹配. 例如创建 com.bit.demo1 的包, 那么会存在一个对应的路径 com/bit/demo1 来存储代码.
如果一个类没有 package 语句, 则该类被放到一个默认包中

详细请看包;

Java的常见包:
java.lang:系统常用基础类(String、Object),此包从JDK1.1后自动导入。
java.lang.reflect:java 反射编程包;
java.net:进行网络编程开发包。
java.sql:进行数据库开发的支持包。
java.util:是java提供的工具程序包。(集合类等) 非常重要
java.io:I/O编程开发包

这些包现在不用太过于了解,后面会随着学习的深入继续了解

继承

继承是面向对象的三大特征之一,也是实现软件复用的重要手段,Java的继承有单继承的特点,每个子类只有一个直接父类;

Java的继承通过extends来实现,实现继承的类是子类,被继承的类是父类;比如水果和苹果的关系,苹果继承了水果,苹果是水果的子类,则苹果是一种特殊的水果;

父类的范围要比子类的大,可以认为父类是大类,子类是小类;
Java里面子类继承父类的语法格式如下:

修饰符 class Wife extends girlfriend_1{
    //类定义部分;
}

在这里wife是你定义的子类的类名,girlfriend_1父类的类名;

 具有继承关系的子类和父类:子类具有父类的全部成员变量,方法和内部类(包括内部接口和枚举),值得提出的是,子类不能继承父类的构造器;

Java学习日志_第8张图片​ 这里面Wife类是girlfriend类的子类;


既然学了继承,那我们就要知道如何去重写父类的方法;

重写父类其实很简单,就是要注意“两同两小一大”规则,“两同”即方法名相同,形参列表相同;“俩小”指的是子类方法返回值类型应该比父类的要小或者相等;“一大”指的是子类方法的访问权限要比父类大或者相等;

Java学习日志_第9张图片

这里,我在Wife类里面重写了wedding方法 ,原本的girlfriend类里面的wedding方法输出的是女朋友,但是经过重写后,变成了妻子;

使用super调用父类中重写的方法、访问父类中被隐藏的字段

 当你想要调用父类中被重写的方法,就可以通过super关键字来实现,super和this一样都不能出现在static修饰的方法中;

多态

先看下面代码:

package xuexi1;

public class girlfriend_1 {
    public String girlfriend="李思敏";
    public void base(){
        System.out.println("父类的普通方法!");
    }
    public void text(){
        System.out.println("父类被覆盖的方法!");
    }
}
class Wife extends girlfriend_1{
    //类定义部分;
    public String girlfriend="王丹";

    public void text(){
        System.out.println("子类覆盖父类的方法!");
    }
    public void sub(){
        System.out.println("子类的普通方法!");
    }
    public static void main(String[] args) {
        girlfriend_1 a=new girlfriend_1();
        System.out.println(a.girlfriend);
        a.base();
        a.text();
        Wife b=new Wife();
        System.out.println(b.girlfriend);
        b.base();
        b.text();
        girlfriend_1 c=new Wife();
        System.out.println(c.girlfriend);
        c.base();
        c.text();
        //c.sub;
    }
}

其中创建了三个引用变量a,b,c;其中a,b编译时类型和运行时类型完全相同,但是c编译时类型为girlfriend,但是他在引用时类型为Wife类型这就会出现多态了;下面是多态的一些特点;

  1. 多态的前提1:是继承
  2. 多态的前提2:要有方法的重写
  3. 父类引用指向子类对象,如:Animal a = new Cat();
  4. 多态中,方法调用编译看左边,运行看右边;变量调用编译看左边,运行也看左边;

编译看左边的意思是,Javac编译代码的时候,会看左边的父类有没有这个变量,如果没有,则编译失败;

多态的好处:使用父类作为参数,可以接受所以子类对象,体现多态的扩展性与遍历; 

强制类型转换

1.基本类型的强转:只能在数值类型之间进行,这里所说的数值类型包括整形,字符型和布尔型;但是要注意的是,数值类型类型和布尔类型之间不能相互转换;

2.引用类型之间的转换只能在具有继承关系的两个类之间转换,如果试图将一个父类类型的实例转换成子类实例;

为了能够更好的了解类型转化,我看见一个讲的比较好的博客;

向上转型和向下转型
 

instanceof

用来判断一个对象是否是一个类或者其子类,实现类的实例,如果是则返回true,否则返回false;

使用格式:

对象名 + instanceof + 类名 

多态的使用 

前提:多态对象把自己看做是父类类型

  1. 成员变量: 使用的是父类的
  2. 成员方法: 由于存在重写现象,所以使用的是子类的
  3. 静态成员: 随着类的加载而加载,谁调用就返回谁的

 组合

组合和继承都是实现类复用的手段,他们两个个有个的优点和缺点;

Java学习日志_第10张图片

 组合和继承的联系

初始化快

初始化块是Java类中的第四种成员(前面依次有成员变量和方法和构造器),一个类里面有多个初始化块,相同类型的初始化块之间有顺序,前面定义的初始化块先执行,后面定义的初始化块后执行;初始化块的语法格式为:

[修饰符] class {

        //初始化块的可执行代码;

}

 初始化块的修饰符自能是static,使用static修饰的的初始化块被称为类初始化块,没有static修饰的初始化块被称为实例初始化块;

 包装类

原始类型: boolean,char,byte,short,int,long,float,double

包装类型:Boolean,Character,Byte,Short,Integer,Long,Float,Double

包装类创建的是对象,拥有方法和字段,对象的调用都是通过引用对象的地址,基本类型不是,还有就是包装类是引用传递,基本类型是值传递;

处理对象

1.打印对象和oStringt方法,当你创建一个对象然后直接用sout打印对象时;

Java学习日志_第11张图片

 运行结果:Java学习日志_第12张图片

可以看出,直接输出对象名实际上就是输出对象toString方法的返回值;

toString方法是Object类里面的一个实例方法,所有的Java类都是Object类的子类,因此所有的Java对象都有toString方法,它是一个”自我描述“的方法,该方法通常会用来实现一个功能:当程序员直接打印该对象时,系统将会输出该对象的自我描述信息,用来告诉外界该对象具有的状态信息;

2.==和equals方法

  • ==运算符:如果判断的是两个基本类型变量,且都是数值类型,那么只要这两个变量的值相等就返回true,不相等就返回false;如果判断的是引用变量,那么只有当两个变量指向同一个对象是才会返回true,不然返回false
  • equals方法: equals方法是Object的一个实例方法,并且我们可以通过重写来改变equals判同的条件;

 抽象类:

抽象方法和抽象类:

  • 抽象方法和抽象类必须使用abstract修饰符来修饰,抽象方法也是:,抽象方法不能有方法体;
  • 抽象类不能被实例化,无法使用new关键字来调用抽象类的构造器类创建抽象类的实例。即使抽象类里面不含抽象方法,这个抽象类也不能创建实例;
  • 抽象类可以包含成员变量,方法,构造器,初始化块,内部类(接口,枚举)5种成分,抽象类的构造器不能用于创建实例,主要是用于被子类调用;
  • 含有抽象方法的类,只能被定义为抽象类;

接口:

和类定义不同,接口不是使用class关键字,而是使用interface关键字,接口定义格式如下:

[修饰符]   interface  接口名  extends  父接口1,父接口2......

{

        零个到多个常量定义......

        零个到多个抽象方法定义......

        零个到多个内部类,接口,枚举定义......

        零个到多个私有方法,默认方法或类方法定义......

}

接口中成员的特点 :

  • 成员变量只能是常量,并且默认public static final修饰;
  • 接口中没有构造器;
  • 成员方法只能是抽象方法,默认修饰符public static;
  • JDK7以前:接口只能定义抽象方法;
  • JDK8的新特性:接口中可以定义有方法体的方法;
  • JDK9的新特性:接口中可以定义私有方法;

接口和类的区别:

  • 类和类的关系:继承关系,不能多继承,但是可以多层继承;
  • 类和接口的关系:实现关系,可以但实现,也可以多实现,还可以在继承一个类的同时实现多个接口;
  • 接口和接口的关系:继承关系,可以单项继承,也可以多项继承;

 JDK8以后接口中新增的方法:

  • 允许在接口中定义默认方法,需要使用关键字default修饰;

           作用:解决接口升级的问题

接口中默认方法的定义格式: 

  •  格式:public default 返回值类型 方法名(参数列表){ }
  • 范例: public default void show(){ }

接口中默认方法的注意事项

  •  默认方法不是抽象方法,所以不强制重写,但是如果被重写,重写的时候去掉default关键字
  • public可以省略,但是default不能省略;
  • 如果实现了多个接口,多个接口中存在相同名字的默认方法,子类就必须对该方法进行重写;

  集合

1.集合的概念:集合是Java中提供的一种容器,用来储存多个数据;

2.集合和数组的区别:

  • 数组:数组的长度是固定的,存储的数据类型要相同,可以存储基本数据类型和引用数据类型;
  • 集合:集合的长度不是固定的,存储的数据类型可以不同,只能存储引用数据类型;

注意,用集合来存储数据的时候 存储不同类型的数据很不安全,于是我们可以使用泛型来实现集合中只能存储相同类型的数据;

集合基本分为两类:

1.Collection:单列集合,添加数据时,每次只能添加一个元素;

2.Map:双列集合,添加数据时,每次添加一对元素;

Collection

Java学习日志_第13张图片

Collextion是单列集合的祖宗接口,它的功能是全部单列集合都可以继承使用的;

Java学习日志_第14张图片

 这是Collection中的一些方法;

小细节:contains方法的底层是通过equals方法来判断是否存在的;

所以如果集合中存储的是自定义对象,也想通过contains方法来判断是否包含,那么在Javabean类中,一定要重写equals方法;

 Collection集合通用遍历方式

因为Collection集合有set儿子,而set系类集合是没有索引的,所以普通的for循环遍历实现不了;

Collection通用的遍历方式有:  

迭代器遍历:

迭代器遍历最大的特点是不依赖索引;

Java学习日志_第15张图片

Java学习日志_第16张图片

 细节注意点:

1,当你遍历完后再次使用next方法,系统会报错NoSuchElementException;

2,迭代器遍历完毕,指针并不会归位,如果还想要遍历,就要重新构造新的迭代器;

3,循环中只能使用一次next方法;

4,迭代器遍历时,不能用集合的方法进行增加或者删除,但是当你想要删除元素的时候,可以通过迭代器的删除方法删除;

增强for遍历;

增强for的底层就是迭代器Iterator,为了简化iterator的代码书写的;

使用对象:所有的单列集合和数组都能使用;

Java学习日志_第17张图片

小细节:修改第三方变量的值不会影响集合中的元素; 

Lambda表达式遍历;

Java学习日志_第18张图片

当你遍历的时候想要删除元素的时候就选择迭代器遍历啥也不干就选择增强for循环Lambda表达式

 List系列集合:添加的元素是有序的,可重复,有索引;

List实现子类的特点:

  1. List集合类中元素有序(即添加顺序和取出顺序一致)、 且可重复
  2. List集合中的每个元素都有相对应的顺序索引,支持索引
  3. List中的元素都对应一个整数型的序号记载其在容器中的位置,可以根据其序号存取容器中对应的元素。

List集合在继承Collection集合的基础上可以通过索引来进行元素的增删查改;

Java学习日志_第19张图片

小细节:根据remove来删除元素时,会优先选择根据索引来进行删除;

List集合遍历元素特有方法:ListIterator

该方法是Iterator的子接口;

Java学习日志_第20张图片

 改迭代器实现了在遍历的时候添加元素;

ArrayList

Java学习日志_第21张图片

LinkedList

底层数据结构是链表,查询慢,增删快,但是如果操作的是首尾元素,速度也是极快的;

LinkedList本身多了很多直接操作首尾元素的特有API(接口);

Java学习日志_第22张图片

Map  

Java学习日志_第23张图片

Map常见API:

Java学习日志_第24张图片

map集合常用API示例:

package Map;

import java.util.HashMap;
import java.util.Map;

public class A01 {
    public static void main(String[] args) {
        //1.创建集合:
        Map m=new HashMap<>();
        //2.添加元素;
        m.put("宁舒意","李思敏");
        m.put("刘洋","迪丽热巴");
        m.put("李心力","彭航博");
        //put方法的细节:
        // 添加和覆盖;
        //在添加数据的时候,如果键不存在,那么直接把键值对对象添加到map集合当中,方法返回null;
        //在添加数据的时候,如果键是存在的,那么会把原有的键值对覆盖,会把覆盖的值进行返回;

//        String s=m.put("刘洋","江疏影");
//        System.out.println(s);

        //删除;
        //String result = m.remove("李心力");
        //System.out.println(result);

        //清空;
        //m.clear();

        //判断是否包含;
//        boolean KeyResult=m.containsKey("宁舒意");
//        System.out.println(KeyResult);
//        boolean ValueResult = m.containsValue("李思敏");
//        System.out.println(ValueResult);

        //判段集合是否为空;

//        boolean result =m.isEmpty();
//        System.out.println(result);

        int size =m.size();
        System.out.println(size);

        //3.打印集合
        System.out.println(m);
    }
}

 Set系列集合:添加的元素是无序,不重复,无索引; 

Java学习日志_第25张图片

泛型 

泛型的好处:

  • 统一数据类型;
  • 把运行时期的问题提前到了编译时期,避免了强制类型转换可能出现的异常,因为在编译阶段类型就能确定下来;

Java学习日志_第26张图片 Java学习日志_第27张图片

 Java学习日志_第28张图片

 应用场景:

        1.如果我们在定义类,方法,接口的时候,如果类型不确定,就可以定义泛型类,泛型方法,泛型接口;

        2.如果类型不确定,但是能知道以后只能传递继承某个体系中的,就可以使用泛型的通          配符;

泛型的通配符:

        关键点:可以限制类型的范围;

Java学习日志_第29张图片

Java学习日志_第30张图片

常见修饰符学习:半成品

你可能感兴趣的:(java,jvm,jar)