2016-09-29 22 views
3

我想transform()一个Dataset在Java中,如下所示:什么是写scala.Function1作为lambda的正确方法?

Function1<Dataset<Long>,Dataset<Long>> withDoubled = (Dataset<Long> numbers) -> numbers.withColumn("doubled",numbers.col("id").multiply(2)); 
spark.range(10).transform(withDoubled).show(); 

然而,Function1<>被标记为错误说有多个抽象函数重载。我如何将它写成lambda?

回答

1

与Scala的Function1使用拉姆达的是不是straigt前进,为lambda与只有一个abstract未实现的功能,这是不正确的Scala的Function1特质的情况下Interface的工作。

我们可以用一个变通方法是,

首先让定义的建设者,这使得失业各地可重复使用,

生成器Function1

package lambdascala; 

import scala.Function1; 

public class Function1WithLambdaBuilder<P1, R> { 

    public static interface Function1LambdaApply<P1, R> { 
    R apply(P1 p1); 
    } 

    private Function1LambdaApply<P1, R> lambda; 

    private Function1<P1, R> function; 

    public Function1WithLambdaBuilder(Function1LambdaApply<P1, R> lambda) { 
    this.lambda = lambda; 
    this.function = new Function1<P1, R>() { 
     @Override 
     public R apply(P1 p1) { 
     return Function1WithLambdaBuilder.this.lambda.apply(p1); 
     } 
    }; 
    } 

    public Function1<P1, R> getFunction() { 
    return this.function; 
    } 

} 

另一个建设者Function2

package lambdascala; 

import scala.Function2; 

public class Function2WithLambdaBuilder<P1, P2, R> { 

    public static interface Function2LambdaApply<P1, P2, R> { 
    R apply(P1 p1, P2 p2); 
    } 

    private Function2LambdaApply<P1, P2, R> lambda; 

    private Function2<P1, P2, R> function; 

    public Function2WithLambdaBuilder(Function2LambdaApply<P1, P2, R> lambda) { 
    this.lambda = lambda; 
    this.function = new Function2<P1,P2, R>() { 
     @Override 
     public R apply(P1 p1, P2 p2) { 
     return Function2WithLambdaBuilder.this.lambda.apply(p1, p2); 
     } 
    }; 
    } 

    public Function2<P1, P2, R> getFunction() { 
    return this.function; 
    } 

} 

您可以按照相同的模式添加更多FunctionN的建设者。

现在我们可以使用这些助建Function1Function2

import lambdascala.Function1WithLambdaBuilder; 
import lambdascala.Function2WithLambdaBuilder; 
import scala.Function1; 
import scala.Function2; 
import java.util.List; 

public class LambdaTry { 

    public static void main() { 

    Function1<List<Long>, List<Long>> changeNothing = 
     new Function1WithLambdaBuilder<List<Long>, List<Long>>(
     // your lambda 
     (List<Long> list) -> list 
    ).getFunction(); 

    Function1<Integer, Integer> add2 = 
     new Function1WithLambdaBuilder<Integer, Integer>(
     // your lambda 
     (Integer i) -> i + 2 
    ).getFunction(); 

    Function2<Integer, Integer, Integer> add = 
     new Function2WithLambdaBuilder<Integer, Integer, Integer>(
     // your lambda 
     (Integer i, Integer j) -> i + j 
    ).getFunction(); 

    System.out.println(add2.apply(12)); 

    System.out.println(add.apply(12, 24)); 

    } 

} 
+1

您可以为每种类型的单'static'工厂方法替换这些令人费解的建设者,使用标准的'Function'和'BiFunction'接口作为输入而不是定义其他接口。 – Holger

+0

@Holger OP希望使用lambda函数创建'scala.Function1','scala.Function2','scala.Function3'等实例。因为他正在使用这些实例和其他一些需要'scala.Function1' ...实例的API,所以我没有看到'Function'或'BiFunction'如何提供帮助。你可以使用这些发布答案吗? –

+1

只需将'Function1LambdaApply '替换为'Function '和'Function2LambdaApply ''BiFunction '。对于三参数函数没有内置类型,但是您没有为三个参数发布示例。 – Holger

相关问题