2022_0112_日结

匿名内部类

匿名内部类指的就是没有名字的类
    一般情况:很少使用具体类的匿名内部类,因为具体类本身就可以new对象
        省去了新建子类(子实现类对象)的过程
    应用场景:就是抽象类和接口中使用最多,其中接口使用最多的!
       固定的格式---->一个类中的某个局部位置使用
               new 类名(一般情况下:都是抽象类)或者接口名(){
 
                   重写抽象类或者接口的抽象方法(){
                       ...
                   }
               };
 
          匿名内部类的本质:就是继承了该抽象类或者实现了接口的子类对象!
​
接口类有多个抽象方法
interface Inter {
    void show();
​
    void show2();
}     //接口
​
​
public class Outer {
    public  void method(){
            Inter i = new Inter() {
             //没有类名  省去了定义子实现类
             @Override
             public void show() {
                 System.out.println("show Inter....");
             }
​
             @Override
             public void show2() {
                 System.out.println("show2 Inter....");
             }
         };
        i.show();
         i.show2();
​
    }
}
​
//测试类
    
    public class InterClassTest {
    public static void main(String[] args) {
              Outer outer = new Outer();
              outer.method();
​
    }
}
抽象类
    abstract class Person {
      public  abstract void work();
}
public class PersonDemo {
    public void method(Person p){
        p.work();
    }
}
class Programmer extends  Person {    //继承子类
    @Override
    public void work() {
        System.out.println("程序员敲代码");
    }
}
​
//测试类
public class InterClassTest {
    public static void main(String[] args) {
       // PersonDemo pd = new PersonDemo();
       // Person person= new Programmer();   //抽象类多态
      //  pd.method(person);
            //需要定义抽象类子类实例
        System.out.println("========================");
​
        //不用将子类定义出来,直接使用匿名内部类
        //匿名内部类
        PersonDemo pd2 = new PersonDemo();
        pd2.method(new Person() {
            @Override
            public void work() {
                System.out.println("程序员一直要工作");
            }
        });   // 等于直接省去了Programmer这个子类
    }
}
​
方法的形式参数传递的如果是一个接口类型,调用方法的时候,需要传递接口的子实现类对象
​
interface Love {
    void love();
}
public class LoveDemo {
    public  void show(Love l){
        l.love();
    }
}
//定义子实现类      类名+Impl  标准格式
public class LoveImpl implements Love {
    @Override
    public void love() {
        System.out.println("学学学学学学学学学...");
    }
}
public class InterClassTest2 {
    public static void main(String[] args) {
        LoveDemo ld = new LoveDemo(); // 访问LoveDemo  show方法
        Love love = new LoveImpl();
                    //子类
        ld.show(love);
        System.out.println("========================");
        //使用匿名内部类
     ld.show(new Love() {
         @Override
         public void love() {
             System.out.println("学习JAVA");
         }
     });
    }
}

  匿名内部类在开发中的使用

   如果方法形式参数是一个抽象类,调用方法的时候实际参数应该传递的当前抽象类的子类对象
   方法的形式参数如果是一个接口类型,调用方法的时候,需要传递接口的子实现类对象
   方法的返回值如果是一个接口,需要接口的子实现类对象

Object里面有clone()方法

protected Object clone()throws CloneNotSupportedException
           创建并返回此对象的副本 
浅克隆     复制一个栈  指向同一个堆内存地址
​
使用克隆方法复制对象    方法受保护
同一个包或者不同包下的子类中使用

重点类

键盘录入Scanner

键盘录入的细节  
  先录入String  再录入int   没问题
  先录入int   再录入String   出现问题
           因为再录入数据时把  回车:enter  当作字符录进去了   
  解决方案:
      1)   String nextLine()   录入一行数据    官方版
                        public String next()    录入指定的字符串
      2)  在录入String之前,重写创建一个新的键盘录入对象
  
  
  以后有int类型的录入   
     可以用String类型录入  然后用 String-->Inter

String类

String类  代表字符串类   是一个常量  
    一旦被创建,其值不能被概念,地址值不发生改变
    地址值指向方法区中的 ConstantPool 常量池 地址
    
    直接输出   为什么不是地址值,因为已经被重写了toString(),就是字符串内容本身
    
    " "空字符序列和null不同
    " "说明有内容,依然可以使用String类型里面的所有功能
    null  空对象  不能使用String方法  否则会造成空指针异常NullPointerException
    
    concat(String str)   拼接功能
    
String(String original)  构造一个字符串常量 里面的参数为   
​
String(char[] value) 
分配一个新的 String ,以便它表示当前包含在字符数组参数中的字符序列。
String(byte[] bytes) 
通过使用平台的默认字符集解码指定的字节数组来构造新的 String 。

要掌握的方法

    String的构造方法
          String() :空参构造
          String(byte[] bytes) :有参构造,里面是字节数组(将byte[]--String)
                   解码过程(将看不懂的内容--->字符--->平台默认字符集现在"utf-8",所以不用带字符集!)
           String(byte[] bytes, int offset, int length) :将一部分字节数组--->字符串
                       参数1:字节数组
                       参数2:指定的位置开始
                       参数3:指定的长度
 
           String(char[] value) :将字符数组---->字符串
 
           String(char[] value, int offset, int count) :将一部分字符数组--->字符串
           参数1:字符数组对象
           参数2:从指定位置开始
           参数3:记录数多少个
 
          String(String original) :构造的字符串对象,参数为字符串常量值
 
 
 
 
 String类的获取功能(都必须掌握)
       public char charAt(int index)获取指定索引出的字符值
       public String concat(String str):拼接功能--->获取新的字符串
                   最传统的拼接使用+:字符串拼接符号
 
      public int indexOf(int ch)返回指定字符第一次出现的字符串内的索引
      public int indexOf(String str):返回指定字符串中子字符串第一次出现索引值
      public int lastIndexOf(int ch):返回指定字符最后一次出现的索引
      public int lastIndexOf(String str)
            String substring(int beginIndex) :从指定位置开始默认截取到末尾--->返回一个新的字符串
 
      String substring(int beginIndex, int endIndex)  :从指定位置开始截取到指定位置结束
                   包前,不包后(只能取到endIndex-1处),返回的一个字符串

面试题

数组中没有length(),String中有没有length(),集合中有没有length()
​
  数组中没有length()方法  有length()属性
  String类有length():获取字符串长度
  集合中没有   是size   获取集合的元素数
String s1 = "hello";
String s2 = new String("hello");
​
有什么区别,分别创建了几个对象?
  前者是常量赋值形式  直接在常量中找,是否存在,如果存在,直接返回常量池地址值  如果不存在,就在常量池中开辟空间,然后把常量池地址值赋值给变量S  从而返回一个地址值
  
  后者
  先new对象   相比前者多了一步在堆内存中开辟空间    
​
​
​
s1是常量赋值,直接在常量中找,是否存在常量,如果存在,返回常量值地址,否则在方法区的常量池中开辟空间创建一个对象
​
s2是创建了两个对象  
      先压栈  进栈内存开辟空间  然后堆内存new创建一个地址值空间,并且地址存在一个常量标记"hello"
   最后在常量池也创建了一个'hello"
          
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值