黑马程序员 java基础24天 基础部分串烧

---------------------- ASP.Net+Unity开发.Net培训、期待与您交流! ---------------------

构造函数与this的使用,构造函数是为了使对象更好的进行初始化,当没有写入构造函数时,系统自带有,如果有写入,则系统不再默认

  每次创建对象,对应的构造函数就会只执行一次。

 this的两个作用:1.用来指示调用对象   2.用于构造函数内部调用  3.用于对象自己与其他对象之间的相同内容的操作

----------------------------------------------------------------------------------------------------------------------

静态:Static 关键字

用法:是一个修饰符,用来修饰成员(成员变量,成员函数)

当成员被静态修饰后,就多了一个调用方式,除了可以被对象调用外,还可以直接被类名调用  类名.静态成员

static 特点:

1.随着类的加载而加载,随着类的消失而消失,寿命最常

2.优先于对象存在,在方法区内

3.被所有对象所共有,在内存中的方法区

4.可以直接可以用类名调用

 

实例变量和类变量的区别:

1.存放位置

  类变量随着类的加载而存在于方法区中

  实例变量随着对象的建立而存在于堆内存中

2.生命周期

  类变量随着类的加载而加载,随着类的消失而消失,寿命最常

  实例变量随着对象的存在而存在,消失而消失

 

注意:1.静态方法只能访问静态成员;非静态方法即可以访问静态也可以访问非静态象存在

     2.静态方法中不可以定义thissuper 关键字,应为静态优先于对象存在

静态有利有弊

 

  利处:对象共享空间,节省空间,直接用类名调用

  弊处:生命周期长,访问出现局限性(静态只能访问静态)

----------------------------------------------------------------------------------------------------------------------

public static void main(String[] args)

主函数:是一个特殊的函数,作为程序的入口,可以被jvm(虚拟机)调用

 

主函数的定义:

public:代表着该函数访问权限是最大的

static:代表主函数随着类的加载已经存在了

void:主函数没有具体的返回值

main:不是关键字,但是一个特殊的单词,可以被JVM识别

(String[] args):函数的参数,参数类型是一个数组,该数组中的元素是字符串,即字符串数组

 

主函数是固定格式的:jvm识别

jvm 在调用主函数时,传入的是new String[0],说明我们也可以向里面传值。java MainDemo haa hh hhi

----------------------------------------------------------------------------------------------------------------------

静态代码块

格式:

static

{

   静态代码块中的执行语句;

}

 

特点:可以多个,随着类的加载而执行,只执行一次,所以是【最先执行的】,

优先于主函数

用途:用于给类进行初始化的。

 

【需求:】验证静态代码块(给类初始化)》构造代码块(给对象【人出生都裸体】初始化)》构造函数(对应对象初始化【有些人出生可能穿衣服】)的执行顺序

----------------------------------------------------------------------------------------------------------------------

对象初始化

Person p = new Person("lll",20)

 

该句话都做了什么事情?

1.因为new用到了Person.class,所以会找到Person.class文家并加载到内存中

2.执行该类中的static代码块。如果有的话,给Person.class类进行初始化。

3.在堆内存中开辟空间,分配内存地址。

4.在堆内存中建立对象的特有属性,并进行默认初始化。如:String 为 null,int 为 0.

5.对属性进行显示初始化。

6.对对象进行构造代码块初始化

7.对对象进行对应的构造函数初始化

8.将内存地址给栈内存中的P变量

----------------------------------------------------------------------------------------------------------------------

设计模式:解决某一类问题最行之有效的方法。

java中23中设计模式

单例设计模式:解决一个类中只能够穿件一个对象。

 

想要保证对象唯一

1.为了避免其他程序过多建立该类对象,那么先禁止其他程序建立对象

2.为了让其他程序访问到该类对象,在自己的类中建立对象。

3.为了方便其他程序对自定义对象的访问,可以对外提供一些访问方式。

 

这三部分怎么用代码体现呢?

1.将构造函数私有化

2.在类中创建一个本类对象

3.提供一个方法可以获取到该对象。

  对于事物该怎么描述,就怎么描述

当需要该事物的对象保证在内存中唯一性时,用以上三步就可。

先初始化对象

称为:饿汉式

class Single

{

  private Single(){}

  private Single s = new Single();

  public static Single getInstance(){

     return s;

   }

}

对象是方法被调用时,才初始化,也叫做对象延时加载

称为:懒汉式

类一加载Single s=NULL。当要调用时才创建对象。

class Single

{

  private Single(){}

  private Single s = null;

  public static Single getInstance(){

     if(s == null){

    synchronized(Single.class){

  if(s == null){

      s = new Single()

        return s;

}}}}

}

----------------------------------------------------------------------------------------------------------------------

要求:获取一段程序运行的时间

原理:获取程序开始和结束的时间并相减即可

 

当代码完成优化后,就解决了这类问题

这种方式:模板方法设计模式

 

什么是模板方法呢?

在定义功能时,功能的一部分是确定的,但是有一部分是不确定的,

而确定的部分在使用不确定的部分,那么这时我们就把不确定的部分暴露出去,

由该类的子类来完成。

 

abstract class GetTime//用于某一段代码运行时间的类。{

  public final void getTime()//final 是子类不能复写该方法{

    long start = System.currentTimeMillis();//获取当前毫秒值

    runCode();

    long end = System.currentTimeMillis();

    System.out.print("毫秒:"+(end - start));

  }

   public abstract void  runCode();//【不确定部分暴露】抽象类中抽象类留给子类复写

}

class SubTime extends GetTime{

  public void runCode(){

       for(int x=0;x<1000;x++){

          System.out.println(x);

      }

   }

}

class MoBanDemo{

   public static void main(String[] args){

       SubTime sub = new SubTime();

       sub.getTime();

    }

}

 

----------------------------------------------------------------------------------------------------------------------

 

接口:初期理解,可以认为是一个特殊的抽象类

     当抽象类中的方法都是抽象的,那么该类可以通过接口的形式来表示。

class用来定义类

interface 用于定义接口

 

接口定义时,格式特点:

1.接口常见定义:常量,抽象方法

2.接口中的成员都有固定修饰符。

  常量:public static final

  方法:publicabstract

 

记住:接口中的成员都是public的。

 

接口:是不可以创建对象的,因为有抽象方法。

需要被子类实现,子类对接口中的抽象方法全部都覆盖后,子类才可以实例化。

如果子类中没有方法为空,则子类继承了接口的方法,子类也就是一个抽象类了

 

1.接口可以被类多实现,也是对多继承不支持的转换形式,java支持多实现

注意:不能出现子类多实现时,接口中出现同名不同类型【可出现同名同类型】的函数(如下示意),这会导致子类对象调用show方法时,不知道调用那个show。

 

2.接口与接口之间是继承关系,接口与接口之间支持多继承

  没有方法体,不会导致调用父类的函数时,如果多个父类中出现同名同类型不同主体的函数,就会导致子类对象不知道调用哪一个的情况

  当然在多实现中,多个接口中可以出现同名同类型的函数,但是不能出现同名不同类型的函数,原因跟上所述一样

 

接口的特点:

1.接口是对外暴露的规则

2.接口是程序的功能扩展

3.接口可以用来实现

4.类与接口之间是实现关系,而且类可以继承一个类与接口之间可以有继承关系

5.接口与接口之间可以有继承关系

 

接口的出现提高了功能的扩展性,接口型引用指向自己的子类对象,也提高了程序

扩展性(多态),接口降低了功能的耦合性,提高了功能的扩展性,提供了规则

继承是你属于我,接口是你像我中的一个;是体系之外的功能扩展。

----------------------------------------------------------------------------------------------------------------------

多态:某一类事物的多种存在的形态

*例如:动物中猫、狗

*猫这个对象对应的类型是猫类型

    猫 x = new 猫();

*同时猫也是动物中的一种,也可以把猫称为动物

 动物 y = new 猫();

 动物是猫和狗具体事物中抽取出来的父类型

 父类型引用指向了子类对象。

 

【转型】

1.多态的体现

    父类的引用指向了自己的子类对象;

    父类的引用也可以接收自己的子类对象。【不能调用父类中没有,而子类中有的函数】

2.多态的前提

    必须是类与类之间有关系,要么是继承,要么是实现;通常还有一个前提,就是存在覆盖。

3.多态的好处

    多态的出现大大提高了程序的扩展性。

4.多态的弊端

    提高了扩展性,但是只能使用父类的引用访问父类的成员。

5.多态的应用

6.多态的出现代码中的特点(多态使用的注意事项)

子类覆盖父类方法,子类方法权限要不小于父类方法权限

主函数调用这所在类中的方法,只能调用静态方法,主函数是静态的,静态只能调用静态

 

Animals a = new Cat();//父类应用指向子类对象//【类型提升,向上转型】猫-》动物

      a.eat();//父类引用指向子类对象,并调用父类和子类共有函数

      //如果要调用猫的特有方法,如何操作?

    //强制将父类的引用,转成子类类型【向下转型】【不能将父类对象强转型为子类类型】

      Cat c = (Cat)a;

       //我们能转换的是父类应用指向了自己的子类对象时,该引用可以被提升,也可以

//被强制向下转型。

      //多态自始至终都是子类在做着变化。

      c.catchMouse();

      ///a.catchMouse();//父类引用指向子类,不能调用父类中没有,而子类中有的函数

多态中成员的特点:

在多态中非静态成员函数的特点:【因为非静态函数有重写特性】

    在编译时期:参阅引用【类型变量所属的类】中是否有调用的方法,如果有,编译通过;如果没有编译失败。

    在运行时:参阅【对象所属类】中是否有调用方法。

    简单总结:非静态成员函数在多态时,编译看左边,运行看右边。

在多态中成员变量的特点:

    无论编译和运行,都参考左边(引用型变量所属类)

在多态中静态成员函数的特点:

    无论编译和运行,都看考左边。

----------------------------------------------------------------------------------------------------------------------

Object:是所有对象的直接或者间接父类,传说中的上帝。

该类中定义的肯定是所有对象中功能

Object类中的方法:

1.equals()

所有对象都具有可比较性,是不是同一个

 public boolean equals(Object d)

   //通过复写Object类中equals(),而public boolean equals(Demo d)是重载了,当然也是可以的,不过多写了方法。

任何对象都可以比较是否相同,其实就是比较是否具有相同的地址值。

 

2.toString()

  把。。变成字符串

----------------------------------------------------------------------------------------------------------------------

内部类

内部类的方位规则:

 1.内部类可以直接访问外部类中的成员,包括私有。

   之所以可以直接访问外部类中的成员,是因为内部类中持有

   一个外部类的引用:格式: 外部类名.this

 2.外部类要访问内部类,必须创建内部类对象。

 

访问格式:

 1.当内部类定义在外部类的成员位置上,而且非私有,可以在外部其他类中

   可以直接建立内部类对象。

   格式:

    外部类名.内部类名变量名 = 外部类对象.内部类对象

    Outer.Inner in = new Outer( ).new Inner( );

 2.当内部类在成员位置上,就可以被成员修饰符所修饰

    比如:private:将内部类在外部类中进行封装

         static:内部类就具备了静态的特性。

                  当内部类被static修饰后,只能直接访问外部类中的Static成员,出现了访问局限

   在外部其他类中,如何直接访问静态内部类的非静态方法呢?

   new Outer.Inner().function()

   在外部其他类中,如何直接访问static内部类的静态成员呢?

   Outer.Inner.function()

 

注意:当内部类中定义了静态成员,该内部类必须是static

 当外部类中的静态方法访问,内部类时,内部类也要是静态的。

 

内部类的运用范围:

当描述事物时,事物的内部还有事物,该事物用内部类来描述。

因为内部事物在使用外部事物的内容。例如:人体中的心脏。

 

【小帖士:static 是成员修饰符,成员修饰符】

内部类定义在局部时:

1.不可以被成员修饰符修饰

2.可以直接访问外部类的成员,因为持有外部类中的引用

  但是不可以访问它所在的局部中的变量,只能访问被final修饰的局部变量。

void method(final int a)//内部类定义在局部成员中{

   fanil int x = 3;

   class Inner{

       static void function()

       {

           System.out.println(x);

       }

   } 

   new Inner().function();

}

//Outer out = new Outer();

//out.method(7);

//out.method(8);这样是可以的,因为a是局部变量,语句执行完,在栈中a消失。

------------------------------------------------------

【匿名内部类】

1.匿名内部类其实就是内部类的简写格式。

2.定义匿名内部类的前提:

    内部类必须是继承一个类或者实现接口。

3.匿名内部类的格式:new 父类或者接口(){定义子类对象};

4.其实匿名内部类就是一个匿名子类对象,而且这个对象有点胖,可以理解

  为带内容的对象。

5.匿名内部类中定义的方法最好不要超过3个。

 

--------------------------

new AbsDemo(){

  void show()

  {System.out.println("");}

}.show();

--------------------------

AbsDemo ab = new AbsDemo(){

 void show()

  {System.out.println("");}

 void show1(){} 

};

ab.show();

ab.show1();//如果父类或者接口中没有show1方法,编译就错误;因为ab是父类引用。

 

练习:

interface Inner{

   void method();

}

class Test

{//补足代码,通过匿名内部类

   static Inner function(){

       return new Inner(){

                   public void metnod(){

                      System.out.println("method run");

                   }

               };

    }

}

class InnerClassTest{

   public static void main(String[] args){

       Test.function().method();

    }

}

//Test.function().method();

//Test.function():test类中有一个静态的方法function。

//.mehtod():function这个方法运算后的结构是一个对象,而且是一个Inner类型的对象。

//因为只有是Inter类型的对象,才可以调用method方法。

//Inter in = Test.function();

//in.method();

练习:

class InnerTest{

   public static void main(String[] args){

       new Object()//继承上帝{

            public void function(){

            }

       }.function();

    }

}

=====================================================

class Outer{

   int x = 3;//用Outer.this.x

   private class Inner//内部类 内部类可私有private{

       int x = 6;//用this.x

       void function(){

           int x= 4;//内部有就打印内部的

           System.out.println("Inner: "+x);

       }

    }

   void method(){

       Inner in = new Inner();

       in.function();

    }

}

 

class InnerDemo{

    public static void main(String[] args) {

       //Outer out = new Outer();

       //out.method();

       //直接访问内部类中的成员

       //Outer.Inner in = new Outer().new Inner();

       in.function();

    }

}

//-----------------------------------------------------------

class Outer{

   static int x = 3;   

   static class Inner//静态内部类 {

       void function(){

           System.out.println("Inner: "+x);

       }

    }

}

 

class InnerDemo{

   public static void main(String[] args){

       //直接访问内部类中的成员

       //Outer.Inner in = new Outer().new Inner();

       //in.function();

       //在外部其他类中,如何直接访问静态内部类呢?用上面的方法就错误。

       new Outer.Inner().function();

        }

}

----------------------------------------------------------------------------------------------------------------------

异常

1.异常:就是程序在运行是出现不正确情况。

异常由来:问题也是现实生活中一个具体的事物,也可以通过java的类的形式进行描述,并封装成对象。

对于问题的划分:两种:一种是严重的问题,一种非严重的问题。

对于严重的:java通过Error类进行描述。

           对于Error一般不编写针对性的代码对其进行处理。

对于非严重的:java通过Exception类进行描述。

           对于Exception可以使用针对性的处理方式进行处理。

无论Error或者Exception都具有一些共性内容,比如:不正常情况的信息,引发原因等。

Throwable//所有问题的超类。

   |--Error

   |--Exception

2.异常的处理

java提供了特有的语句进行处理

try{

    需要被检测的代码

}

catch(异常类变量){

    处理异常的代码:(处理方式)

}

finally{

    一定会处理的代码;

}

 

3.对捕获到的异常对象进行常见方法操作

 String getMessage():获取异常信息

在函数上声明异常。

便于提高安全性,让调用处进行处理,不处理会编译失败。

 

4.对多异常的处理。

(1).声明异常时,建议声明更为具体的异常,这样处理的可以更具体

(2).对方声明几个异常,就对应有几个catch块,不要定义多余的catch块

   如果对个catch块中的异常出现异常关系,父类异常catch块放在最下面

建议在进行catch处理时,catch中一定要定义具体处理方式。

不要简单定义一句e.printStackTrace(),

也不要简单的就书写一条输出语句。

 

5.自定义异常

因为项目中会出现特有的问题。

而这些问题并未被java所描述并封装对象。

所以对于这些特有的问题可以按照java的对问题封装的思想

将特有的问题,进行自定义的异常封装

 

当要定义自定义异常的信息时,可以使用父类已经定义好的功能。

异常异常信息的传递给父类的构造函数。

 

自定义异常

需求:在本程序中,对于除数是负数,也视为是错误的是无法进行运算的

那么就需要对这个问题进行自定义的描述

当在函数内部出现了throw抛出异常对象,那么就必须要给对应的处理动作。

要么在内部try  catch处理

要么在函数上声明让调用者处理

一般情况下,函数内出现的异常,函数上需要声明。

发现打印的结果中只有异常的名称,没有异常的信息。

因为自定义的异常并未定义信息

 

【如何定义异常信息?】

 因为父类中已经把异常信息的操作都完成了。

 所以子类只要在构造函数,将异常信息传递给父类通过super语句

 那么就可以直接通过getMessage方法获取自定义的异常信息。

自定义异常:必须是自定义类继承Exception

 

继承Exception类的原因:

异常体系有一个特点,因为异常类和异常对象都被抛出

他们都具备可抛性,这个可抛性是Throwable这个体系中独有特点。

只有这个体系中的类和对象才可以被throw和throws操作。

【throw和throws的区别】

throws使用在函数上

throw使用在函数内。

 

throws后面跟的异常类,可以跟多个,用逗号隔开

throw后跟的是异常对象。

 

【对于异常分两种】

1.编译时被检测的异常

2.编译时不被检测的异常,RuntimeException以及其子类

 

【finally】

finally代码块:定义一定执行的代码。

通常用于关闭资源。

finally只有一种情况不会执行,当执行到System.exit(0);finally不会执行

//记住一点:catch是用于处理异常,如果没有catch就代表异常内有处理过,

如果该异常是检测时异常,那么必须声明。

 

class FuShuException  extends Exception{

   private String msg;

   FuShuException (String msg){

       this.msg = msg;

    }

   public String getMessage(){

       return msg;

    }

}

class Demo

{

  int div(int a,int b) throws FuShuException

  {  

      if(b<0)

         throw new FuShuException("不能输入负数!");

      return a/b;

   }

}

class ExceptionDemo{

   public static void main(String[] args) //throws Exception{

          Demo d = new Demo();

          try {

            int x = d.div(4,-1);

            System.out.println(x);

          }

          catch(FuShuException e) {

            System.out.println(e.toString());

            System.out.println("不能输入负数!");

          }

    }

}

class FuShuException  extends Exception{

   FuShuException(String msg){

      super(msg);//父类已经定义了该功能,所以就传给父类出做。

    }

}

class Demo {

  int div(int a,int b) throws FuShuException

  {  

      if(b<0)

         throw new FuShuException("不能输入负数!");

      return a/b;

   }

}

 

 

class ExceptionDemo{

   public static void main(String[] args) //throws Exception{

          Demo d = new Demo();

          try{

            int x = d.div(4,-1);

            System.out.println(x);

          }catch(FuShuException e){

            System.out.println(e.toString());

            System.out.println("不能输入负数!");

          }

    }

}

Exception中有一个特殊的子类异常RuntimeException,运行时异常,

如果在函数内容抛出该异常,函数上可以不用声明,编译一样通过,

如果在函数上声明了该异常,调用者可以不用进行处理,编译一样通过。

之所以不用在函数上声明,是因为不需要让调用者处理。

当该异常发生,希望程序停止,因为在运行时,出现了无法继续运算的情况,

希望停止程序后,对代码进行修正。

自定义异常时,如果该类异常的发生,无法在继续进行运算,

就让自定义异常继承RuntimeException

class Demo {

  int div(int a,int b) {  

      if(b<0)

         throw new ArithmeticException("不能输入负数!");

      return a/b;

   }

}

class ExceptionDemo{

   public static void main(String[] args){

          Demo d = new Demo();

         int x = d.div(4,-1);

         System.out.println(x);

          System.out.println("over");

    }

}

异常在子父类覆盖中的体现:

1.子类在覆盖父类时,如果父类的方法抛出异常,那么子类的覆盖方法,只能抛出父类的异常或者该异常的子类。父类已经有问题了,子类只能抛父类的异常或者异常的子异常

2.如果父类方法抛出多个异常,那么子类在覆盖该方法时,只能抛出父类异常的子集。

3.如果父类或者接口方法中没有异常抛出,那么子类在覆盖方法时,也不可以抛出异常。如果子类方法发生了异常,就必须要进行try处理,绝对不可以抛。

----------------------------------------------------------------------------------------------------------------------

包与包之间进行访问,被访问的包中的类以及类中的成员,需要public修饰不同包中的子类还可以直接访问父类中被protected权限修饰的成员。

 

包与包之间可以使用的权限只有两种,public  protected

              public    protected   default      private

同一个类中      ok          ok          ok      ok

同一个包中      ok          ok          ok      ok

子类                  ok          ok

不同包中        ok

 

注意:一个java文件中不能出现多个共有类

为了简化类名的书写,使用一个关键字:import

import导入的是包中的类

建议:不要写通配符*,需要用到包中的那个类,就导入那个类。






----------------------- ASP.Net+Unity开发.Net培训、期待与您交流! ----------------------详细请查看:www.itheima.com

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值