如何按数据类型过滤rdd?

时间:2019-01-26 14:09:41

标签: scala apache-spark rdd

我有一个rdd,我试图仅针对float类型进行过滤。 Spark rdds是否提供任何这样做的方法?

我有一个csv,我只需要将大于40的浮点值放入新的rdd中即可。为此,我正在检查它是否是float类型的实例并对其进行过滤。当我用!过滤时,所有字符串仍在输出中,当我不使用!时,输出为空。

val airports1 = airports.filter(line => !line.split(",")(6).isInstanceOf[Float])
val airports2 = airports1.filter(line => line.split(",")(6).toFloat > 40)

.toFloat处,我遇到了NumberFormatException,我试图在try catch块中进行处理。

1 个答案:

答案 0 :(得分:3)

由于您有一个纯字符串,并且试图从中获取浮点值,因此实际上并没有按类型进行过滤。但是,如果可以将它们解析为浮动的话。
您可以将flatMapOption一起使用。

import org.apache.spark.sql.SparkSession
import scala.util.Try

val spark = SparkSession.builder.master("local[*]").appName("Float caster").getOrCreate()
val sc = spark.sparkContext

val data = List("x,10", "y,3.3", "z,a")
val rdd = sc.parallelize(data) // rdd: RDD[String]
val filtered = rdd.flatMap(line => Try(line.split(",")(1).toFloat).toOption) // filtered: RDD[Float]
filtered.collect() // res0: Array[Float] = Array(10.0, 3.3)

对于> 40部分,您可以在其后执行另一个过滤器,也可以过滤内部Option
(两者都应或多或少地具有应有的火花懒惰性,因此选择一种对您来说更清晰)

// Option 1 - Another filter.
val filtered2 = filtered.filter(x => x > 40)

// Option 2 - Filter the inner option in one step.
val filtered = rdd.flatMap(line => Try(line.split(",")(1).toFloat).toOption.filter(x => x > 40))

让我知道您是否有任何疑问。