使用filter()方法查找Scala中以数字开头的行

Shi*_*iva 1 syntax scala apache-spark

我是一个python程序员,因为Python API对我的Spark应用程序来说太慢了,所以决定将我的代码移植到Spark Scala API,以比较计算时间.

我试图使用Spark中的Scala API从一个巨大的文件中过滤掉以数字字符开头的行.在我的文件中,有些行有数字,有些有单词,我想要只有数字的行.

所以,在我的Python应用程序中,我有这些行.

l = sc.textFile("my_file_path")
l_filtered = l.filter(lambda s: s[0].isdigit())
Run Code Online (Sandbox Code Playgroud)

这完全符合我的要求.

这是我到目前为止所尝试的.

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(x => x.forall(_.isDigit))
Run Code Online (Sandbox Code Playgroud)

这会抛出一个错误,说char没有forall()函数.

我还尝试使用s.take(1)获取行的第一个字符,并按以下方式对其应用isDigit()函数.

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(x => x.take(1).isDigit)
Run Code Online (Sandbox Code Playgroud)

这也是......

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(x => x.take(1).Character.isDigit)
Run Code Online (Sandbox Code Playgroud)

这也会引发错误.

这基本上是一个小错误,因为我不习惯Scala语法,所以我很难搞清楚它.任何帮助,将不胜感激.

编辑:作为这个问题的答案,我尝试编写该函数,但我无法在我的应用程序中的filter()函数中使用它.将函数应用于文件中的所有行.

Iho*_*nko 6

在Scala中,索引语法使用parens ()而不是括号[].您的Python代码的确切翻译将是这样的:

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(_(0).isDigit)
Run Code Online (Sandbox Code Playgroud)

更常用的第一个符号提取head方法是使用方法:

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(_.head.isDigit)
Run Code Online (Sandbox Code Playgroud)

如果您的文件包含空行,这两种方法都将失败.

如果是这样,那么你可能想要这个:

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(_.headOption.map(_.isDigit).getOrElse(false))
Run Code Online (Sandbox Code Playgroud)

UPD.

由于好奇指出map(predicate).getOrElse(false)Option可以减短为exists(predicate):

val l = sc.textFile("my_file_path")
val l_filtered = l.filter(_.headOption.exists(_.isDigit))
Run Code Online (Sandbox Code Playgroud)