方法引用、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、付费专栏及课程。

余额充值