• 类和对象的深度剖析


    提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档

    文章目录

    • 1.类的实例化
    • 2.this的引用
    • 3.构造方法
    • 4.默认初始化
    • 5.就地初始化
    • 6.static成员
    • 8.代码块
    • 9.内部类

    1.类的实例化

    1. class Dog
    2. {
    3. public int age;
    4. public String name;
    5. public void set(int age,String name)
    6. {
    7. this.age=age;
    8. this.name=name;
    9. }
    10. public void dayin()
    11. {
    12. System.out.println(this.age);
    13. System.out.println(this.name);
    14. }
    15. public void bark()
    16. {
    17. System.out.println("狗叫");
    18. }
    19. public void eat()
    20. {
    21. System.out.println("狗吃");
    22. }
    23. }
    24. public static void main1(String[] args) {
    25. Dog dog=new Dog(); //类的实例化
    26. dog.age=3;
    27. dog.name="wang";
    28. System.out.println(dog.age);
    29. System.out.println(dog.name);
    30. }

    2.this的引用

    我们一起来看一段代码

    1. class Dog
    2. {
    3. public int age;
    4. public String name;
    5. public void set(int a,String b)
    6. {
    7. age=a;
    8. name=b;
    9. }
    10. public void dayin()
    11. {
    12. System.out.println(age);
    13. System.out.println(name);
    14. }
    15. public static void main2(String[] args) {
    16. Dog dog1=new Dog();
    17. Dog dog2=new Dog();
    18. dog1.set(3,"wang");
    19. dog2.set(4,"li");
    20. dog1.dayin();
    21. dog2.dayin();
    22. }

    像这种情况如果我们把3,"wang",4,"li",参数传过去,set函数接受的时候不知道到底最后赋值给了dog1的age.name还是dog2的age和name,因此我们需要this,代码修改如下

    1. class Dog
    2. {
    3. public int age;
    4. public String name;
    5. public void set(int a,String b)
    6. {
    7. this.age=a; //this可以认为当dog1传叁的时候,this相当于dog1,a b的值分别赋值给了dog1的age和name,dog2传叁的时候,同样的this就相当于dog2
    8. this.name=b; //
    9. }
    10. public void dayin()
    11. {
    12. System.out.println(age);
    13. System.out.println(name);
    14. }
    15. public static void main2(String[] args) {
    16. Dog dog1=new Dog();
    17. Dog dog2=new Dog();
    18. dog1.set(3,"wang");
    19. dog2.set(4,"li");
    20. dog1.dayin();
    21. dog2.dayin();
    22. }

    3.构造方法

    构造方法是指方法名和类名相同的方法,当我们不去定义这个方法的时候,系统会默认定义这个方法。

    1. class Student
    2. {
    3. public int age;
    4. public String name;
    5. public String grade;
    6. public void set(int age,String name,String grade)
    7. {
    8. this.age=age;
    9. this.name=name;
    10. this.grade=grade;
    11. }
    12. public void pint()
    13. {
    14. System.out.println(age+" "+name+" "+grade);
    15. }
    16. public void pint()
    17. {
    18. System.out.println(age+" "+name+" "+grade);
    19. }
    20. public Student()
    21. {
    22. //System.out.println("不带参数的构造方法");
    23. this(7,"wang","java7"); //这里也可以通过this这个语句来给参数赋值,但是这个语句必须在第一行
    24. pint();
    25. }
    26. public Student(int age,String name,String grade)
    27. {
    28. System.out.println("带参数的构造方法");
    29. this.age=age;
    30. this.name=name;
    31. this.grade=grade;
    32. pint();
    33. }
    34. public static void main(String[] args) {
    35. Student student2=new Student();
    36. }

     4.默认初始化  是指即使我们没有给成员变量赋值时,但在对象空间被申请好了以后,对象中的成员变量已经设置好了成员变量

    bite     0

    char    '\u0000’

    short   0

    int       0

    long     0L

    boolean   false

    float     0.0f

    double  0.0f

    String      null

    1. class Dog
    2. {
    3. public int age;
    4. public String name;
    5. public void dayin()
    6. {
    7. System.out.println(age);
    8. System.out.println(name);
    9. }
    10. }
    11. public static void main3(String[] args) {
    12. Dog dog3=new Dog();
    13. System.out.println(dog3.age+" "+dog3.name);
    14. }

     

    5.就地初始化       是指在声明成员变量时直接赋值

    1. class Girl
    2. {
    3. int age=7; //
    4. String hobby="打篮球";
    5. public void fun()
    6. {
    7. System.out.println("age="+age+" "+"hobby="+hobby);
    8. }
    9. }
    10. public static void main11(String[] args) {
    11. Girl girl=new Girl();
    12. girl.fun();
    13. }

     6.static 成员

    static 成员我们在访问的时候可以通过对象访问,也可以通过类名访问,最好通过类名访问

    1. class Boy
    2. {
    3. public static int age=1;
    4. public static String name="lisi";
    5. }
    6. public static void main15(String[] args) {
    7. Boy boy=new Boy();
    8. System.out.println(boy.age);
    9. System.out.println(boy.name);
    10. System.out.println(Boy.age);
    11. System.out.println(Boy.name);
    12. }

    1. class Boy
    2. {
    3. public static int age=1;
    4. public static String name="lisi";
    5. // public static int age=1;
    6. // static String name="wang";
    7. public static int fun()
    8. {
    9. return age;
    10. }
    11. }
    12. public static void main(String[] args) {
    13. Boy boy=new Boy();
    14. System.out.println(boy.fun());//对象访问
    15. System.out.println(Boy.fun());//类名访问
    16. }

    当我们不创建对象时也可以通过类名访问,与对象存不存在没有关系

    1. class Boy
    2. {
    3. public static int age=1;
    4. public static String name="lisi";
    5. }
    6. public static void main15(String[] args) {
    7. //Boy boy=new Boy();
    8. // System.out.println(boy.age);
    9. // System.out.println(boy.name);
    10. System.out.println(Boy.age);
    11. System.out.println(Boy.name);
    12. }

     

     static修饰的成员方法中,不可以出现this、非静态的变量、非静态的成员方法

    1. class Boy
    2. {
    3. public int age=1;
    4. public static String name="lisi";
    5. public static int fun()
    6. {
    7. return age; //静态方法中不能引用非静态变量age
    8. }
    9. }
    10. class Boy
    11. {
    12. public int age=1;
    13. public static String name="lisi";
    14. public static void set(int age,String name)
    15. {
    16. this.age=age; //静态方法中不可以引用非静态变量 this
    17. this.name=name;
    18. }
    19. }
    20. class Boy {
    21. public int age = 1;
    22. public static String name = "lisi";
    23. public void gun() {
    24. System.out.println("打印");
    25. }
    26. public static void dayin() {
    27. this.gun(); //静态方法中不可以引用非静态方法,因为非静态方法中有this参数
    28. }
    29. }

    8.代码块

    主要分为静态代码块和实例代码块,静态代码块用来初始化静态变量而实例代码块用来初始化非静态代码块

    1. class Monther
    2. {
    3. public int age;
    4. public int month;
    5. public static String name;
    6. {
    7. this.age=1;
    8. this.month=8;
    9. System.out.println("实例代码块");
    10. }
    11. static
    12. {
    13. name="wang";
    14. System.out.println("静态代码块");
    15. }
    16. // static
    17. //{
    18. //name="li";
    19. //System.out.println("静态代码块");
    20. //}
    21. public Monther()
    22. {
    23. System.out.println("不带参数的构造方法");
    24. }
    25. }
    26. public static void main(String[] args) {
    27. Monther monther=new Monther();
    28. }

    根据我们所想打印的不带参数的构造方法,

    然而打印出来的却是这样一个结果,那么这又是什么原因呢?这是因为静态代码块中的静态成员变量在类加载时已经 开辟空间并初始化,实例代码块在创建对象完成后就被执行了,所以三者执行的先后顺序分别是静态代码块、实例代码块、构造方法

    静态代码块不管生成多少对象,只会执行一次

    1. class Monther
    2. {
    3. public int age;
    4. public int month;
    5. public static String name;
    6. {
    7. this.age=1;
    8. this.month=8;
    9. System.out.println("实例代码块");
    10. }
    11. static
    12. {
    13. name="wang";
    14. System.out.println("静态代码块");
    15. }
    16. // static
    17. //{
    18. //name="li";
    19. //System.out.println("静态代码块");
    20. //}
    21. public Monther()
    22. {
    23. System.out.println("不带参数的构造方法");
    24. }
    25. }
    26. public static void main(String[] args) {
    27. Monther monther1=new Monther();
    28. Monther monther2=new Monther();
    29. }

     第二次我们可以看到并没有打印静态代码块,说明静态代码块只执行一次

    当有多个静态代码块时,静态代码块按照先后顺序序执行

    1. class Monther
    2. {
    3. public static int age;
    4. public int month;
    5. public static String name="li"; //1 只要是static修饰的变量我们都可以认为是一个代码块
    6. { //3
    7. age=1;
    8. System.out.println("实例代码块");
    9. }
    10. static //2
    11. {
    12. name="wang";
    13. System.out.println("静态代码块");
    14. }
    15. static //4
    16. {
    17. age++;
    18. name="xiao";
    19. System.out.println("也是静态代码块");
    20. }
    21. public Monther() //5
    22. {
    23. System.out.println("不带参数的构造方法");
    24. }
    25. public static void main(String[] args) {
    26. Monther monther1=new Monther();
    27. System.out.println(Monther.age);
    28. System.out.println(Monther.name);
    29. }

     9.内部类   

    内部类简单来说就是一个类当中含有另一个类

    1.如何获取实例内部类对象?需要创建外部的和内部的对象

    1. class Outer
    2. {
    3. public int age1 = 3;
    4. public int age2 = 7;
    5. public int age3= 2
    6. class Inter
    7. {
    8. public int age4 = 3;
    9. public int age5 = 4;
    10. public void dayin()
    11. {
    12. System.out.println(age1); //内部类当中可以访问所有外部类的成员变量
    13. System.out.println(age2);
    14. System.out.println(age3);
    15. System.out.println(age4);
    16. System.out.println(age5);
    17. }
    18. }
    19. }
    20. public static void main(String[] args) {
    21. Outer outer=new Outer(); //创建外部和内部的对象
    22. Outer.Inter inter=outer.new Inter();
    23. inter.dayin();
    24. }

    在实例内部类当中不能有静态的成员量,如果想要使用 需要加上 final

    1. class Outer
    2. {
    3. public int age1 = 1;
    4. public int age2 = 7;
    5. class Inter
    6. {
    7. public static int age3=8;//实例内部类当中不能有静态成员变量
    8. public static final int age=8; //加上 final age成为了一个常量
    9. }

    如果实例内部类和外部类有相同的成员变量,优先访问内部的成员变量

    1. class Outer
    2. {
    3. public int age1 = 1;
    4. public int age2 = 7;
    5. class Inter
    6. {
    7. public int age1 = 3;
    8. public int age3 = 4;
    9. public void dayin()
    10. {
    11. System.out.println(age1);
    12. }
    13. }
    14. public static void main3(String[] args) {
    15. Outer outer=new Outer();
    16. Outer.Inter inter=outer.new Inter();
    17. inter.dayin();
    18. }

    在本题中优先访问内部的age1,所以最终打印出来的结果应该是3.

     如果非要访问外部的,我们可以采取两种方式

    1. class Outer
    2. {
    3. public int age1 = 1;
    4. public int age2 = 7;
    5. class Inter
    6. {
    7. public int age1 = 3;
    8. public void dayin()
    9. {
    10. System.out.println(Outer.this.age1);//第一种方式直接利用类
    11. Outer outer = new Outer();第二种方式创建一个引用变量
    12. System.out.println(outer.age1);
    13. }
    14. }

    实例内部类总结1:内部类方法当中可以直接访问外部类的成员变量

                              2.当内部类和外部当中出现相同的成员变量时优先访问自己的,如果实在想访问,就用  类名.this.同名成员来访问也可以创建一个外部对象,通过引用的方式来访问

    3.外部类中,不能直接访问实例内部类成员,如果要访问需要先创建内部类的对象

    静态内部类

    静态内部类被static修饰的成员内部类:在静态类当中只能访问外部类中的静态成员,如果确实想访问,需要通过外部类对象的引用

    1. class Outer
    2. {
    3. public static int age1=1;
    4. public static int age2=2;
    5. int age4=8;
    6. static class Inter
    7. {
    8. public static int age3=3;
    9. public static void dayin()
    10. {
    11. System.out.println(age1);
    12. System.out.println(age2);
    13. System.out.println(age3);
    14. Outer outer=new Outer(); //age4是外部类当中非静态成员需要通过外部类对象的引用
    15. System.out.println(outer.age4);
    16. }
    17. }
    18. }
    19. public class text {
    20. public static void main14(String[] args) {
    21. Outer.Inter inter=new Outer.Inter();//创建静态内部类对象时,不需要先创建外部类对象
    22. inter.dayin();
    23. }

     

  • 相关阅读:
    计算机毕业设计——基于html汽车商城网站页面设计与实现论文源码ppt(35页) HTML+CSS+JavaScript
    大数据学习(11)-hive on mapreduce详解
    通过Orika的MapperFacade实现对象与对象的转化
    前端格式化工具
    超详细的顺序表(附源码)
    动物园
    竞赛 题目:基于LSTM的预测算法 - 股票预测 天气预测 房价预测
    C语言面试题 - 结构体对齐
    事件绑定(onmouseout,onmouseover)
    华清 c++ day5 9月12
  • 原文地址:https://blog.csdn.net/m0_70386582/article/details/126186574