【问题标题】:From Scala to Java 1.8从 Scala 到 Java 1.8
【发布时间】:2014-12-19 08:58:56
【问题描述】:

我想编写一个解析 csv 日志文件的 Spark 程序,用分隔符“;”分割单词并创建一个对象,其属性值是位于特定位置的单词。 代码在 Scala 中看起来像这样,但我在将其转换为 Java 1.8 时遇到了麻烦(我想在 Java 中使用 lambda 表达式)。

val file = sc.textFile("hdfs:/../vrLogs.csv") 
class VREvent(val eventTimestamp: String, val deviceID: String, val eventType: String, val itemGroupName: String)
val vrEvents = file.map(_.split(';')).filter(_.size == 32).map(a => new VREvent(a(0), a(1), a(6), a(13))) 

我不知道如何将这部分翻译成 Java:.map(a => new VREvent(a(0), a(1), a(6), a(13)))

我试过这个(没有过滤器部分):

JavaRDD<String> records = lines.flatMap(s -> Arrays.asList(s.split(";"))).map(a -> new CDREvent(a[0], a[1], a[6], a[13])); 

【问题讨论】:

  • 请格式化您的代码!
  • Java 1.8 中的流也有 map 方法。是什么阻止了你?
  • 您可以使用a.get(0),而不是a[0] 从Java 列表中获取单个元素;后一种语法只能用于数组,不能用于列表。
  • 当然,您也可以跳过Arrays.asList 并传递String[] 而不是List&lt;String&gt;
  • 您收到该错误是因为您的flatMap 正在从Arrays.asList 生成的列表中获取所有项目并将它们作为流的单独元素发送;因此,在您的 map 中,a 的类型是 String,而不是 List&lt;String&gt;

标签: java scala lambda bigdata apache-spark


【解决方案1】:

假设linesStream&lt;String&gt;

List<CDREvent> events =
    lines
        .map(s -> s.split(";"))
        .filter(a -> a.length == 32)
        .map(a -> new CDREvent(a[0], a[1], a[6], a[13]))
        .collect(Collectors.toList());

将每一行映射到一个String[],过滤掉所有长度不是32的数组,将每个String[]映射到一个CDREvent,并将它们收集到一个新列表中。

【讨论】:

  • 谢谢@DavidConrad 这解决了我的问题并帮助我更好地理解它的工作方式!
猜你喜欢
  • 2015-07-20
  • 2016-01-20
  • 1970-01-01
  • 1970-01-01
  • 2023-03-09
  • 2015-07-17
  • 2020-11-11
  • 2022-08-14
  • 2019-02-10
相关资源
最近更新 更多