我有两个数组:
val customers = Array("Alice", "Bob", "Mike","Charly")
val customersLen = customers.length
val items = Array("milk", "bread", "butter", "apples", "oranges")
val itemsLen = items.length
val size = (customersLen*itemsLen)-1
我可以在数组中创建这两个数组的笛卡尔乘积,如下所示:
val cartesianProd= for(i <- 0 to size) yield (customers(i % customersLen ),items(i % itemsLen ))
输出将是:
cartesianProd: scala.collection.immutable.IndexedSeq[(String, String(] = 矢量((爱丽丝,牛奶(, (鲍勃,面包(, (迈克,黄油(, (查理,苹果(, (爱丽丝,橙子(, (鲍勃,牛奶(, (迈克,面包(, (查理,黄油(, (爱丽丝,苹果(,(鲍勃,橙子(,(迈克,牛奶(,(查理,面包(, (爱丽丝,黄油(,(鲍勃,苹果(,(迈克,橙子(,(查理,牛奶(, (爱丽丝,面包(,(鲍勃,黄油(,(迈克,苹果(,(查理,橙子((
现在我想从这个数组生成一个数据帧。重用之前的逻辑,所以我写了:
val dfCustItem = Seq(for(i <- 0 to size ) yield(customers (i % customersLen ),items(i % itemsLen ))).toDF("customer","item")
但是我收到以下错误:
java.lang.IllegalArgumentException: 要求失败: 列不匹配。旧列名 (1(:值 新列名 (2(:名称,斯卡拉的项目。Predef$.require(Predef.scala:224( at org.apache.spark.sql.Dataset.toDF(Dataset.scala:397( at org.apache.spark.sql.DatasetHolder.toDF(DatasetHolder.scala:44( ... 48 省略
据我了解,这是因为yield在名为值的单个列中返回对(客户,项目(,并且toDF期望两个独立的列(不确定此列的名称是否相关(
我该如何解决这个问题? 也就是说,在两个独立的列中产生循环的输出
你有一个额外的Seq
所以只是删除它应该可以工作
val dfCustItem = (for(i <- 0 to size ) yield(customers (i % customersLen ),items(i % itemsLen ))).toDF("customer","item")
解释:
如您所见,for(i <- 0 to size) yield (customers(i % customersLen ),items(i % itemsLen ))
已经scala.collection.immutable.IndexedSeq[(String, String)]
,添加Seq
将生成Seq[scala.collection.immutable.IndexedSeq[(String, String)]]
而您需要在Seq
中Tuple2
元素