Java – how to link bifunctions?

I want to link bifunctions, just like in the chainwanted method in the following code example

Bifunction takes function as the parameter of andthen Is it possible to link bifunctions in some way?

The code here cannot be compiled because of this. I can't convert bifunction to function

import java.util.function.BiFunction;
import java.util.function.Function;

import org.openqa.selenium.remote.RemoteWebDriver;

public class Wf {

    BiFunction<RemoteWebDriver,WfParams,RemoteWebDriver> init = this::init;
    BiFunction<RemoteWebDriver,RemoteWebDriver> wait = this::wait;

    BiFunction<RemoteWebDriver,RemoteWebDriver> chainNow = init
            .andThen(d -> {
                System.out.println("--------------");
                return null;
            });

    BiFunction<RemoteWebDriver,RemoteWebDriver> chainWanted = init
            .andThen((BiFunction) wait);

    public RemoteWebDriver init(RemoteWebDriver d,WfParams params) {
        System.out.println("init(d,params)");
        return d;
    }

    public RemoteWebDriver wait(RemoteWebDriver d,WfParams params) {
        System.out.println("Wf.wait(d,params)");
        return d;
    }

    public static void main(String[] args) throws Exception {
        new Wf().start();
    }

    private void start() {
        chainNow.apply(null,null);
    }
}

Solution

Linking one function to another works naturally, because the return value of the first function is passed as a parameter to the next function, and the return value of the function is passed as a parameter to subsequent functions, and so on This does not work for bifunctions because they have two parameters The first parameter is the return value of the previous function, but what is the second parameter? It also explains why bifunction allows andthen to be linked to a function instead of another bifunction

However, this means that if there is some way to provide a value for the second parameter, one bifunction can be linked to another bifunction This can be done by creating an auxiliary function that stores the value of the second parameter in a local variable You can then convert bifunction to function by capturing the local variable from the environment and using it as the second parameter

This is what it looks like

BiFunction<RemoteWebDriver,RemoteWebDriver> chainWanted = this::chainHelper;

RemoteWebDriver chainHelper(RemoteWebDriver driver,WfParams params) {
    return
        init.andThen(rwd -> wait.apply(rwd,params))
            .apply(driver,params);
}

// ...

chainWanted.apply(driver,params);

The chainhelper method saves the params parameter for later capture We call init Andthen () to link But this requires a function, and waiting is a bifunction Instead of using methods to reference this:: wait, we use lambda expressions

rwd -> wait.apply(rwd,params)

It captures parameters from the lexical context This gives a lambda expression that takes a parameter and returns a value, so it is now a function that wraps the wait, which is a bifunction This is an example of partial application or currying Finally, we use the bifunction generated by the apply () call to pass the original parameters

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>