Java day23——方法引用、RandomAccessFile(了解)

方法引用

方法引用: Lambda 的简化

  1. 方法引用是对Lambda的优化, 换句话说是在Lambda内部调用了方法
  2. Lambda内部调用的方法使用的参数, 就是Lambda传递进来的参数
  3. 方法引用也遵循了之前学习的面向对象的理论知识
    普通方法需要对象来调用
    静态方法需要类来调用
 public static void print(String s, Printable p) {
        p.print(s);
    }

    public static void main(String[] args) {
        print("Hello Lambda",
                s -> {System.out.println(s);});
        /**
         * s -> System.out.println(s)
         * 1.参数s 直接传给了 println 方法使用
         * 2.System.out 对象本身就是存在的
         * 3.println() 这个方法本身也是存在的
         * 4.println方法的参数就是 接口方法的参数
         * -- 就可以简化
         */
        
        // 使用 方法引用 来简化Lambda
        print("Hello Lambda", System.out::println);
    }

通过对象名引用成员方法

步骤

  1. 准备一个函数式接口
  2. 准备一个方法 method, 用于接收 函数式接口 作为方法参数
  3. 准备一个类, 类中要有一个成员方法printUpperCase
  4. 因为要使用Lambda表达式, 所以需要调用 method 方法
    并且需要在Lambda表达式内部调用 printUpperCase
    printUpperCase方法的参数就是Lambda传递进来的参数
@FunctionalInterface
public interface Printable {
    void print(String s);
}
public class MyObjectMethod {
    public void printUpperCase(String s) {
        System.out.println(s.toUpperCase());
    }
public class Demo {
    public static void method1(String s, Printable p) {
        p.print(s);
    }

    public static void main(String[] args) {
       /* method1("hello", s -> {
            // 1.先创建MyObjectMethod对象
            MyObjectMethod obj = new MyObjectMethod();
            // 2.调用 printUpperCase 这个方法
            obj.printUpperCase(s);
        });*/

        // 使用方法引用来优化
        /*
            1.对象已经存在 obj
            2.方法已经存在 printUpperCase
         */
        MyObjectMethod obj = new MyObjectMethod();
        method1("hello", obj::printUpperCase);
    }

通过类名引用静态方法

步骤

  1. 准备一个函数式接口
  2. 准备一个方法 cal, 用于接收 函数式接口 作为方法参数
  3. 准备一个类 Math , 类中要有一个静态方法 abs
  4. 因为要使用Lambda表达式, 所以需要调用 cal 方法
    并且需要在Lambda表达式内部调用 Math.abs 静态方法
    abs 方法的参数就是Lambda传递进来的参数
@FunctionalInterface
public interface Calcable {
    int calAbs(int n);
}
public class Demo {
    public static int cal(int n, Calcable c) {
        return c.calAbs(n);
    }

    public static void main(String[] args) {
        /*int t = cal(-10, n->{return Math.abs(n);});
        System.out.println(t);*/
        /**
         * 1.方法 已经存在 abs
         * 2.类存在 Math
         */
        // 使用方法引用来优化
        int t = cal(-10, Math::abs);
        System.out.println(t);
    }

通过super引用成员方法

步骤

  1. 准备一个函数式接口
  2. 准备一个父类, 父类中有一个普通成员方法 hi(String)
  3. 准备一个子类[, 可以重写hi方法]
  4. 子类中要有一个sayHello方法, 用于接收 函数式接口 作为方法参数
  5. 在子类中再次准备一个方法, show(), 用于调用sayHello
    可以传递Lambda表达式
    需要在Lambda表达式中 调用 父类的hi方法
    就会用到 super.hi(参数)
  6. 效果展示, 在主方法中调用show()
public interface Greetable {
    void greet(String message);
}
public class Human {
    public void hi(String message) {
        System.out.println("hi Human!" + message);
    }
}
public class Man extends Human {
    // 重写的父类的hi方法
    public void hi(String message) {
        System.out.println("Hi Man!" + message);
    }
    // 定义一个sayHello, 目的是为了传入Lambda表达式
    public void sayHello(String s, Greetable g) {
        g.greet(s);
    }
    // 这个方法的目的, 是为了调用 sayHello
    public void show() {
       /* sayHello("吃了吗", s->{
            // 调用父类的hi方法
            super.hi(s);
        });*/
        /**
         * 1.super对象已存在
         * 2.方法hi已存在
         */
        sayHello("吃了吗", super::hi);
    }

    public static void main(String[] args) {
        new Man().show();
    }
}

通过this引用成员方法

步骤

  1. 准备一个函数式接口
  2. 准备一个类, 准备一个普通成员方法 buyHouse
  3. 类中要有一个 marry 方法, 用于接收 函数式接口 作为方法参数
  4. 在类中再次准备一个方法, show(), 用于调用 marry
    可以传递Lambda表达式
    需要在Lambda表达式中 调用 自己的 buyHouse 方法
    就会用到 this.buyHouse(参数)
  5. 效果展示, 在主方法中调用show()
public interface Richable {
    void buy(String str);
}
public class Husband {
    public void buyHouse(String str) {
        System.out.println("在" + str + "买了一套三居室");
    }
    public void marry(String str, Richable ric) {
        ric.buy(str);
    }
    public void show() {
        /*marry("北京三环内", s->{
            this.buyHouse(s);
        });*/
        /**
         * this 已经存在
         * buyHouse 已经存在
         */
        // 方法引用优化
        marry("北京三环内", this::buyHouse);
    }

    public static void main(String[] args) {
        new Husband().show();
    }

类的构造器引用

Lambda表达式中使用了类的构造器

public interface PersonBuilder {
    // 通过传入的name参数 构造一个Person对象并返回
//    Person builderPerson(String name);
    Person builderPerson();

public class Person {
    private String name;

    public Person() {
        System.out.println("无参构造方法");
    }

    public Person(String name) {
        this.name = name;
        System.out.println("有参构造方法");
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

public class Demo {
    public static void build(String name, PersonBuilder builder) {
        /*Person person = builder.builderPerson(name);
        System.out.println(person.getName());*/
        Person person = builder.builderPerson();
        System.out.println(person.getName());
    }

    public static void main(String[] args) {
//        build("赵丽颖",
//                name -> new Person(name));
        // 构造器本身是存在的
        build("赵丽颖", Person::new);

        /*build("赵丽颖",
                () -> new Person());*/

    }

数组的构造器引用

Lambda表达式中创建了一个数组

public interface ArrayBuilder {
    // 根据n - 数组长度, 来创建一个新的数组
    int[] builderArray(int n);
}

public class Demo {
    public static int[] builder(int n, ArrayBuilder arrBuild) {
        return arrBuild.builderArray(n);
    }

    public static void main(String[] args) {
//        int[] array = builder(10, n -> new int[n]);
        int[] array = builder(10, int[]::new);
        System.out.println(array.length);
    }
}

RandomAccessFile

可读可写的类,不属于流, 基于文件指针的操作
文件指针停留在哪里, 就可以操作文件的哪个位置
也可以手动指定文件指针的位置
指针位置的操作:
void skipBytes(跳过字节个数)
long getFilePointer() - 得到当前指针位置
void seek(long) - 指针定位到指定的位置
读写:
readInt/readDouble…
writeInt/writeDouble…

@Test
    public void test01Write() throws IOException {
        // 文件如果不存在, 会创建新的文件
        // 文件如果存在, 原内容上直接写入新内容进行覆盖, 没有清空
        RandomAccessFile rw = new RandomAccessFile("a.txt", "rw");
        rw.write("你".getBytes());
        rw.close();
    }

    @Test
    public void test02Write() throws IOException {
        RandomAccessFile rw = new RandomAccessFile("a.txt", "rw");
        // 查看rw对象初始的文件指针位置
        long filePointer = rw.getFilePointer();
        System.out.println("初始指针位置: " + filePointer);
        // 跳过前面6个字节, 再开始写入
        rw.skipBytes(6);
        System.out.println("跳过6个字节后位置: " + rw.getFilePointer());
        rw.write("吃了吗".getBytes());
        System.out.println("写完内容后的位置: " + rw.getFilePointer());
        rw.close();
    }

    @Test
    public void test03Write() throws IOException {
        RandomAccessFile rw = new RandomAccessFile("a.txt", "rw");

        rw.writeDouble(Long.MAX_VALUE);

        System.out.println(rw.getFilePointer());
        rw.close();
    }
 @Test
    public void test01Read() throws IOException {
        RandomAccessFile rw = new RandomAccessFile("a.txt", "rw");

        double d = rw.readDouble();
        System.out.println(d);
        rw.close();
    }
@Test
    public void test02WriteAndRead() throws IOException {
        RandomAccessFile rw = new RandomAccessFile("a.txt", "rw");
        rw.writeLong(10l);
        // 设置文件指针位置
        rw.seek(0l);
        double d = rw.readLong();
        System.out.println(d);
        rw.close();
    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值