我开始使用Scala,Spark和MLlib。 我想从Kaggle
实现一个示例数据格式很糟糕,我有很多问题需要清理和准备数据来处理它们。我求你帮忙。
数据是:
PassengerId,Survived,Pclass,Name,Sex,Age,SibSp,Parch,Ticket,Fare,Cabin,Embarked
1,0,3,"Braund, Mr. Owen Harris",male,22,1,0,A/5 21171,7.25,,S
2,1,1,"Cumings, Mrs. John Bradley (Florence Briggs Thayer)",female,38,1,0,PC 17599,71.2833,C85,C
3,1,3,"Heikkinen, Miss. Laina",female,26,0,0,STON/O2. 3101282,7.925,,S
4,1,1,"Futrelle, Mrs. Jacques Heath (Lily May Peel)",female,35,1,0,113803,53.1,C123,S
5,0,3,"Allen, Mr. William Henry",male,35,0,0,373450,8.05,,S
我在
等空字段中出错...,“”,......(第一行,字段“小屋”)
...,“A / 5 21171”,....(也是第一行,字段“票”)
我想过滤空字段的行(从我的RDD中删除它们)以及那些包含这样的票据的行 A / 5 21171 (I只想要数字。)
再次感谢您的帮助! ;)
答案 0 :(得分:4)
而不是RDD
,您应该考虑使用DataSet
来提高性能和易用性 - 特别是如果您不熟悉Scala。采用DataSet
方法,您可以这样做:
val titanicDs = sparkSession.read
.option("header", true)
.csv("titanic.csv")
.na
.drop
.withColumn("TicketSplit", split($"Ticket", " "))
.withColumn("Ticket", when(size($"TicketSplit") === "2", $"TicketSplit".getItem(1)).otherwise($"TicketSplit".getItem(0)))
.drop("TicketSplit")
这里有很多事情发生:
header
选项设置为true,以便Spark意识到第一行是数据的标头强制结构,并在DataFrame
中使用这些列名称。na
方法返回DataFrameNaFunctions
对象,very helpful用于处理丢失的数据。在这种情况下,na.drop
的组合会删除包含任何数据null
的所有行。TicketSplit
的新临时列,我使用精彩的functions
library将空格字符上的原始Ticket
数据拆分为任意长度的数组1(如果只有一个数字)或2(如果有文本后跟空格和数字)。 when
库中的otherwise
和functions
根据Ticket
列中数组的大小修改原始TicketSplit
列。无论TicketSplit
列中数组的大小如何,最终只能通过在索引0处获取1元素数组的第一个元素或在索引1处获取2元素数组的第二个元素来保留该数字。 TicketSplit
列,因为它已达到目的。