我是靠谱客的博主 年轻乌龟,最近开发中收集的这篇文章主要介绍Java学习(第二周)四.Java面对对象final抽象方法抽象类,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

在这一周的学习中,我学了面对对象这一章,这一章相比于C++多了许多新东西,同时这一章也是Java学习中的关键部分,所以我对此下了很大功夫。

面向对象具有三大特征:封装性、继承性和多态性,而面向过程没有继承性和多态性,并且面向过程的封装只是封装功能,而面向对象可以封装数据和功能。所以面向对象优势更明显。

目录​​​​​​​

四.Java面对对象

this

super

Package

单例模式

类型转换              

final

String类中常用的方法

         抽象方法

         抽象类

         接口

内部类

a) 非静态内部类

b)静态内部类

         匿名类

         局部内部类

         本地类

默认方法


四.Java面对对象

栈的特点如下:

  1. 栈描述的是方法执行的内存模型。每个方法被调用都会创建一个栈帧(存储局部变量、操作数、方法出口等)

  2. JVM为每个线程创建一个栈,用于存放该线程执行方法的信息(实际参数、局部变量等)

  3. 栈属于线程私有,不能实现线程间的共享!

  4. 栈的存储特性是“先进后出,后进先出”

  5. 栈是由系统自动分配,速度快!栈是一个连续的内存空间!

堆的特点如下:

  1. 堆用于存储创建好的对象和数组(数组也是对象)

  2. JVM只有一个堆,被所有线程共享

  3. 堆是一个不连续的内存空间,分配灵活,速度慢!

方法区(又叫静态区)特点如下:

  1. JVM只有一个方法区,被所有线程共享!

  2. 方法区实际也是堆,只是用于存储类、常量相关的信息!

  3. 用来存放程序中永远是不变或唯一的内容。(类信息【Class对象】、静态变量、字符串常量等)

this

this的本质就是“创建好的对象的地址”! 由于在构造方法调用前,对象已经创建。因此,在构造方法中也可以使用this代表“当前对象” 。

C++中是this->name;

而在Java中为this.name=name;

super

可以用来修饰属性,方法,构造器

f(){}
super.f();

构造方法的第一句总是super()

1、当子类与父类有同名的属性时,可以通过super属性的方式调用父类中生命的属性。

2、当子类重写父类的方法后,在子类中若想调用父类中被重写的方法时,需用super.的方法

3、super修饰构造器,通过在子类中使用super列表参数的形式调用父类中制定的构造器

        a、在构造器内部,super(参数列表)必须声明在首行

        b、在构造器内部,this(参数列表)或super(参数列表)只能出现一个

        c、当构造器中不显示的调用this(参数列表)或super(参数列表)默认调用父类中的空参                 构造器

public childclass extends fatherclass{
   public childclass(){
          super();//默认的
           System.out.println();
    }
}     //子->父->object



注意:在类中,用static声明的成员变量为静态成员变量,也称为类变量static成员变量只有一份。被该类的所有对象共享!!在static方法中不可直接访问非static的成员。

static修饰的成员变量和方法,从属于类。普通变量和方法从属于对象的。

没有static需要有对象才能调用。加static可直接调用,不用再new。

为什么this super不能用在static方法中

this : 代表当前自身类的对象,可以调用当前类的构造方法,成员变量和成员方法等

super : 代表对父类的引用 , 可以调用父类构造方法,成员变量和方法

因为static方法和类的实例(对象)是两码事,它只在类装载的时候初始化,被称作类级变量(属于类);而类的实例是在程序运行的时候(即Java命令的时候)初始化,被称作对象级变量(属于对象);

this表示这个类的当前实例,super表示父类的当前实例,static是属于类的,this是类的一个对象,

this指针是指向类的对象,在实例化对象时jvm会在堆区分配内存给一个具体的对象,this指针指向这个对象。而类中的static域始终是在静态区分配内存,this指向堆区,所以不能调用。

因此this super不能用在static方法中

Package

为了便于管理,将处理同一方面的问题的类放在同一个目录下,引入了包

包定义:

package 包名;    //声明

package(包)  域名倒着写 cn.gst.oo

cn.gst.oo.User user=new cn.gst.oo.User();(有点繁琐)  //使用其他包的类

//使用其他包的类,用import.   import cn.gst.oo.User;

使用 import 导入单个类    import 包名+类名;

直接导入指定类   import example.Test;

使用 import 语句导入指定包下全部类  import example.*;

单例模式 :  只有一个实例存在,给别的类用

什么是单例模式?

1. 构造方法私有化

2. 静态属性指向实例

3. public static的 getInstance方法,返回第二步的静态属性

饿汉式单例模式:未使用就已经实例化。

//GiantDragon 提供了一个public static的getInstance方法,外部调用者通过该方法获取12行定义的对象,而且每一次都是获取同一个对象。 从而达到单例的目的。
private test(){
//通过私有化其构造方法,使得外部无法通过new 得到新的实例。
}
private static test instance = new test();//准备一个类属性,指向一个实例化对象。 因为是类属性,所以只有一个
public static txst getInstance(){
//public static 方法,提供给调用者获取定义的对象
return instance;
}

懒汉式单例模式:使用时才实例化。

 private test(){
//私有化构造方法使得该类无法在外部通过new 进行实例化
}
private static test instance=null;
//准备一个类属性,用于指向一个实例化对象,但是暂时指向null
public static test getInstance(){
//public static 方法,返回实例对象
if(null==instance){
//第一次访问的时候,发现instance没有指向任何对象,这时实例化一个对象
            instance = new test();
//返回 instance指向的对象
        }

什么时候使用饿汉式,什么时候使用懒汉式:

饿汉式是立即加载的方式,无论是否会用到这个对象,都会加载。


懒汉式,是延迟加载的方式,只有使用的时候才会加载。 
使用懒汉式,在启动的时候,会感觉到比饿汉式略快,因为并没有做对象的实例化。 但是在第一次调用的时候,会进行实例化操作,感觉上就略慢。

有比较充分的启动和初始化时间,就使用饿汉式,否则就使用懒汉式

类型转换:

子类转父类(向上转型),一定可以的

 父类转子类(向下转型),所以要进行强转

instanceof  类名 判断一个引用所指向的对象,是否是父类,或者子类

(二元运算符,左边是对象,右边是类,当是右边类或子类创建的对象时,返回true,否则返回false)

Object obj = new String("
");
if(obj instanceof String){
//判断所指向的对象
String str = (String)obj;
System.out.println(str.charAt(0));
}else if(obj instanceof StringBuffer){
StringBuffer str = (StringBuffer) obj;
System.out.println(str.charAt(0));
}

向上转型:父亲引用指向子类对象或者 子类转为父类(小转大,不需要强转)

向下转型:子类引用指向父类对象 或者父类转子类(大转小,需强转)

C++在类中默认private,Java默认为default                                         

修饰符同一个类同一个包 子类所有类
private
default
protected
public  

final

1.修饰变量:被他修饰的变量不可改变,一旦赋了初始值,就不能被重新赋值

2.修饰方法:该方法不可被子类重写,但可以被重载

3.修饰类:修饰的类不能被继承。例如String,Math。

4.修饰引用:h引用被修饰成final,表示该引用只有1次指向对象的机会,依然通过h引用修改对象的属性值hp,因为hp并没有final修饰

final Hero h;
        h  =new Hero();
        h  =new Hero();//错误
        h.hp = 5;

5.常量指的是可以公开,直接访问,不会变化的值

 public static final int itemTotalNumber = 6;

①  首先介绍一下String类中常用的方法

1.在java中共有三种方法将两个字符串连接

第一种方法:使用+;

public static
String mergedString1(String string1,String string2) {
return
string1 + string2;
}

 第二种方法:使用concat();

public static String mergedString2(String string1, String string2) {
return string1.concat(string2);
}

 第三种方法:使用append();

public static
StringBuffer mergedString3(String string1, String string2) {
StringBuffer sb = new StringBuffer(string1);
return sb.append(string2);
}

2.判断两个String对象相等

String str1 = "the light";
String str2 = new String(str1);
System.out.println( str1  ==  str2); //false

str1和str2的内容一定是一样的!但是,并不是同一个字符串对象

String str1="gg";
String str2="gg";    
System.out.println( str1  ==  str2); //true       

//编译器发现已经存在现成的"the light",那么就直接拿来使用,而没有进行重复创建

3.通常比较字符串时,用equals

String str1="gg";
String str2="gg";
System.out.println(str2.equals(str1)); //true

4.提取字符 :charAt()

String s1="love";
System.out.println(s1.charAt(3)); //输出为e

5.字符串的长度:length()

String s1="love";
System.out.println(s1.length());


 

6.比较两个字符串(忽略大小写):equalsIgnoreCase()
 

String s1="A";
String s2="a";
System.out.println(s2.equalsIgnoreCase(s1));  //忽略大小写    A==a; true

7.字符串中是否包含:indexOf()

System.out.println(s1.indexOf("Java"));//检测字符串s1中是否包含Jav

String s1 = "core Java";
System.out.println(s1.indexOf("Java"));//检测字符串s1中是否包含Java。true
//若无返回-1。

8.替换 :replace()

String s1 = "core Java";
String s=s1.replace(' ','&');//将s1中空格换为&

9.是否以 ...开头startsWith()

String s1="How are you?";
System.out.println(s1.startsWith("How"));//是否以How开头

10.是否以...结尾:endsWith()

String s1="How are you?";
System.out.println(s1.endsWith("you"));//是否以you结尾

11.提取子字符串:substring()

String s=" ";
String s1="How are you?";
s=s1.substring(4);//提取子字符串,从4开始.  //are you?
System.out.println(s);
String s=" ";
String s1="How are you?";
s=s1.substring(4,7);//提取子字符串,从[4,7),不包括7,    //are
System.out.println(s);

12.转小写:toLowerCase()

String s1="H";
s=s1.toLowerCase();//.转小写
System.out.println(s);
//h

13.转大写:toUpperCase()

String s1="h";
s=s1.toUpperCase();//.转大写
System.out.println(s);
//H

14.去除收尾的字符串,中间不去:trim()

String s2="   How old are you!!  ";
s=s2.trim();   //去除收尾的字符串,中间不去
System.out.println(s);  //How old are you!!
System.out.println(s2);//   How old are you!!  //s2不变

抽象方法

      使用abstract修饰的方法,没有方法体,只有声明。定义的是一种“规范”,就是告诉子类必须要给抽象方法提供具体的实现。

抽象类

      包含抽象方法的类就是抽象类。通过abstract方法定义规范,然后要求子类必须定义具

实现。通过抽象类,我们就可以做到严格限制子类的设计,使子类之间更加通用。

示例:

public abstract class Animal{
//规范子类
       abstract public void shout();
        public static void main(String[] args){
         Animal a=new Animal();//错误
         Animal a=new Dog();
         }
}   ; //子类必须实现
class Dog  extends  Animal{
    public void  shout(){
             System.out.println();//必须有
      }
}


为父类增加一个抽象方法 ,继承父类后,这些子类就必须提供不一样的抽象方法实现。

抽象类的使用要点:
1.有抽象方法的类只能定义成抽象类
2.抽象类不能实例化,即不能用new实例化
3.抽象化可以包含属性,方法,构造方法,但构造方法不能用来new实例,只能用来被子类调用
4.抽象类只能用来被继承
5.抽象方法只能被子类实现

实例化:只是单纯的把对象 new 一下就行了 例:Student st=new Student();这样就行了
初始化:是在实例化之后完成的,先实例化对象,只给对象属性赋值,然后初始化这个对象

在Java中引入了接口这个概念

        接口就是比“抽象类”还“抽象”的“抽象类”,可以更加规范的对子类进行约束。全面地专业地实现了:规范和具体实现的分离。

       抽象类还提供某些具体实现,接口不提供任何实现,接口中所有方法都是抽象方法。接口是完全面向规范的,规定了一批类具有的公共方法规范。

声明格式

[访问修饰符]
interface 接口名
[extends
父接口1,父接口2…]
{
常量定义;
方法定义;
}

定义接口的详细说明:

1.访问修饰符:可以是默认或者public
2.接口名:和类名采用相同命名机制
3.extends:接口可以多继承
4.常量:接口中的属性只能是常量, int M=111;
总是:public static final修饰,不写也是
5.方法:接口中的方法只能是public abstract,不写也是

注意:接口内所有方法多是抽象化,不用再写abstract ,因此必须重写。
关键字: implements(接口) 
 

java的类只有单继承,接口有多继承

抽象类和接口的区别:
区别1:子类只能继承一个抽象类,不能继承多个
             子类可以实现多个接口
区别2:抽象类可定义public,protected,package,private。静态和非静态属性。final和非final属性。
但是接口中声明的属性,只能是public,静态,final的,即便没有显式的声明。

接下来介绍一些  内部类

在Java中内部类主要分为成员内部类(非静态内部类、静态内部类)、匿名内部类、局部内部类。

成员内部类(可以使用private、default、protected、public任意进行修饰。

a) 非静态内部类(外部类里使用非静态内部类和平时使用其他类没什么不同)

 i. 非静态内部类必须寄存在一个外部类对象里。因此,如果有一个非静态内部类对象那么一定存在对应的外部类对象。非静态内部类对象单独属于外部类的某个对象。

ii. 非静态内部类可以直接访问外部类的成员,但是外部类不能直接访问非静态内部类成员。

iii. 非静态内部类不能有静态方法、静态属性和静态初始化块。

iv. 外部类的静态方法、静态代码块不能访问非静态内部类,包括不能使用非静态内部类定义变量、创建实例。

非静态内部类可以直接在一个类里面定义
实例化语法:  new 外部类().new 内部类() 或 外部类对象.new 非静态内部类();

public class 外部类 {
...
// 非静态内部类,只有一个外部类对象存在的时候,才有意义
// 战斗成绩只有在一个英雄对象存在的时候才有意义
class 非静态内部类 {
...
public void 方法名() {
...
}
}
public static void main(String[] args) {
外部类 对象 = new 外部类();
// 实例化内部类
// 非静态内部类对象只有在一个外部类对象存在的时候才有意义
// 所以其实例化必须建立在一个外部类对象的基础之上
}
}



在内部类中使用外部成员变量:  Outer.this.age    内部类名.this.外部成员变量。
在内部类中使用内部类的成员变量: this.age    this.内部成员变量
在内部类中使用局部变量:    age

b)静态内部类

 i. 定义方式:

static
class
ClassName {
//类体
}

 ii. 使用要点:

       1. 当一个静态内部类对象存在,并不一定存在对应的外部类对象。 因此,静态内部类的实例方法不能直接访问外部类的实例方法。

       2. 静态内部类看做外部类的一个静态成员。 因此,外部类的方法中可以通过:“静态内部类.名字”的方式访问静态内部类的静态成员,通过 new 静态内部类()访问静态内部类的实例。

在一个类里面声明一个静态内部类与非静态内部类不同,静态内部类的实例化 不需要一个外部类的实例为基础,可以直接实例化

除了可以访问外部类的私有静态成员外,静态内部类和普通类没什么大的区别
实例化语法:new 外部类.静态内部类();

匿名类

匿名类指的是在声明一个类的同时实例化它,使代码更加简洁精练
通常情况下,要使用一个接口或者抽象类,都必须创建一个子类
有的时候,为了快速使用,直接实例化一个抽象类,并“当场”实现其抽象方法。
既然实现了抽象方法,那么就是一个新的类,只是这个类,没有命名。
这样的类,叫做匿名类

public abstract class 外部类 {
...
public abstract void 方法();
public static void main(String[] args) {
外部类 对象 = new 外部类(){
//当场实现方法
public void 方法() {
...
}
};
对象.方法();
System.out.println(对象); //通过打印对象,可以看到这个对象属于&&这么一个系统自动分配的类名
}
}

注意:  1. 匿名内部类没有访问修饰符。

           2. 匿名内部类没有构造方法。因为它连名字都没有那又何来构造方法呢。

//在匿名类中使用外部的局部变量,外部的局部变量必须修饰为final。
注:在jdk8中,已经不需要强制修饰成final了,如果没有写final,不会报错,因为编译器偷偷的帮你加上了看不见的final

局部内部类

局部内部类是定义在方法内部的,作用域只限于本方法。

public class 外部类{
public void 方法1() {
//作用域仅限于该方法
class 内部类 {
public void 方法2() {
...
}
}
new 内部类().方法2();
}
public static void main(String[] args) {
new 外部类().方法1();
}
}

本地类


本地类可以理解为有名字的匿名类
内部类与匿名类不一样的是,内部类必须声明在成员的位置,即与属性和方法平等的位置。
本地类和匿名类一样,直接声明在代码块里面,可以是主方法,for循环里等等地方

public abstract class 外部类 {
...
public abstract void 方法();
public static void main(String[] args) {
//与匿名类的区别在于,本地类有了自定义的类名
class 本地类 extends 外部类
public void 方法() {
//进行重写
}
}
本地类 对象
=new 本地类();
对象.方法();
}
}


 

默认方法是JDK8新特性,指的是接口也可以提供具体方法了,而不像以前,只能提供抽象方法。

public interface 接口名 {
public void 方法1();
default public void 方法2() {
//接口增加了一个默认方法2,这个方法有实现体,并且被声明为了default
...
}
}

最后

以上就是年轻乌龟为你收集整理的Java学习(第二周)四.Java面对对象final抽象方法抽象类的全部内容,希望文章能够帮你解决Java学习(第二周)四.Java面对对象final抽象方法抽象类所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(33)

评论列表共有 0 条评论

立即
投稿
返回
顶部