>source

다음 열이있는 두 개의 데이터 프레임이 있습니다.

df1.columns
//Array(ts, id, X1, X2)

df2.columns
//Array(ts, id, Y1, Y2)

내가해야 할 일

val df_combined= df1.join(df2, Seq(ts,id))

다음 열로 끝납니다.어레이 (TS, ID, X1, X2, TS, ID, Y1, Y2)...에 나는 공통 칼럼이 떨어질 것이라고 기대할 수 있습니다. 추가 해야하는 추가 기능이 있습니까?

조인 열을 문자열의 서열열 (열 이름)으로 정의한 경우 열을 복제해서는 안됩니다. 아래의 내 대답을보십시오.

stackoverflowuser20102021-08-21 08:48:45
  • 답변 # 1

    누군가가 Spark-SQL을 사용하고 있고 똑같은 것을 얻고 싶다면 사용할 수 있습니다.사용조인 쿼리의 절.

    val spark= SparkSession.builder().master("local[*]").getOrCreate()
    spark.sparkContext.setLogLevel("ERROR")
    import spark.implicits._
    val df1= List((1, 4, 3), (5, 2, 4), (7, 4, 5)).toDF("c1", "c2", "C3")
    val df2= List((1, 4, 3), (5, 2, 4), (7, 4, 10)).toDF("c1", "c2", "C4")
    df1.createOrReplaceTempView("table1")
    df2.createOrReplaceTempView("table2")
    spark.sql("select * from table1  inner join  table2  using (c1, c2)").show(false)
    /*
    +---+---+---+---+
    |c1 |c2 |C3 |C4 |
    +---+---+---+---+
    |1  |4  |3  |3  |
    |5  |2  |4  |4  |
    |7  |4  |5  |10 |
    +---+---+---+---+
    */
    

  • 답변 # 2

    모범 사례는 열 이름을 모두 DF에 합류하고 그에 따라 떨어지는 것입니다.

    df1.columns=[id, age, income]
    df2.column=[id, age_group]
    df1.join(df2, on=df1.id== df2.id,how='inner').write.saveAsTable('table_name')
    

    은 중복 열의 오류가 발생하는 동안 오류를 반환합니다.

    이 대신 이것을 시도해보십시오.

    df2_id_renamed= df2.withColumnRenamed('id','id_2')
    df1.join(df2_id_renamed, on=df1.id== df2_id_renamed.id_2,how='inner').drop('id_2')
    

  • 답변 # 3

    내부 조인은 기본 조인이 Spark에서이며, 아래의 간단한 구문입니다.

    leftDF.join(rightDF,"Common Col Nam")
    

    다른 조인은 아래 구문을 따를 수 있습니다.

    leftDF.join(rightDF,Seq("Common Columns comma seperated","join type")
    

    열 이름이 일반적이지 않은 경우

    leftDF.join(rightDF,leftDF.col("x")===rightDF.col("y),"join type")
    

    OP는 가입 후 중복 된 열을 떨어 뜨리고 그 지점을 놓친 것 같아요.

    Vaibhav2021-08-22 00:39:09
  • 답변 # 4

    여러 테이블을 함께 합류 한 후, 중복이 발생하는 경우 DF의 열의 이름을 바꾸는 간단한 함수를 통해 실행됩니다. 대안으로, 이러한 중복 열도 삭제할 수 있습니다...에

    이름열이있는 테이블입니다[ 'ID', '이름', 'DateID', '설명']그리고날짜열이있는 테이블입니다[ 'ID', '날짜', '설명'], 열ID그리고설명합류 한 후 복제됩니다.

    Names= sparkSession.sql("SELECT * FROM Names")
    Dates= sparkSession.sql("SELECT * FROM Dates")
    NamesAndDates= Names.join(Dates, Names.DateId== Dates.Id, "inner")
    NamesAndDates= deDupeDfCols(NamesAndDates, '_')
    NamesAndDates.saveAsTable("...", format="parquet", mode="overwrite", path="...")
    

    dedupedfcol.다음과 같이 정의됩니다.

    def deDupeDfCols(df, separator=''):
        newcols= []
        for col in df.columns:
            if col not in newcols:
                newcols.append(col)
            else:
                for i in range(2, 1000):
                    if (col + separator + str(i)) not in newcols:
                        newcols.append(col + separator + str(i))
                        break
        return df.toDF(*newcols)
    

    결과 데이터 프레임에는 열이 포함됩니다.[ 'ID', '이름', 'DateID', '설명', 'ID2', '날짜', 'Description2']...에

    사과이 답변은 파이썬에 있습니다 -나는 스칼라에 익숙하지 않지만, 이것은 내가이 문제를 찍었을 때 일어난 질문이었습니다. 나는 다른 것입니다. ...에

  • 답변 # 5

    이것을 시도해보십시오,

    val df_combined= df1.join(df2, df1("ts")=== df2("ts") &
    &
     df1("id")=== df2("id")).drop(df2("ts")).drop(df2("id"))
    

  • 답변 # 6

    이것은 예상되는 동작입니다.DataFrame.join.메소드는 SQL 조인과 동일합니다

    SELECT * FROM a JOIN b ON joinExprs
    

    중복 된 열을 무시하려는 경우 이후에 이루어 지거나 관심있는 열을 선택하십시오. 암호화하려는 경우 부모를 사용하여이를 사용할 수 있습니다.데이터 프레임:

    val a: DataFrame= ???
    val b: DataFrame= ???
    val joinExprs: Column= ???
    a.join(b, joinExprs).select(a("id"), b("foo"))
    //drop equivalent
    a.alias("a").join(b.alias("b"), joinExprs).drop(b("id")).drop(a("foo"))
    

    또는 별명 사용 :

    //As for now aliases don't work with drop
    a.alias("a").join(b.alias("b"), joinExprs).select($"a.id", $"b.foo")
    

    equi-joins의 경우 다음 중 하나를 사용하는 특수 단축 구문이 있습니다.

    val usingColumns: Seq[String]= ???
    a.join(b, usingColumns)
    

    또는 AS.

    val usingColumn: String= ???
    a.join(b, usingColumn)
    

    조인 조건에서 사용되는 열의 복사본 만 유지합니다.

    선택 대신 중복 열을 삭제할 수 있습니까?

    Neel2021-08-21 08:48:45

    예,하지만 부모를 통해서만 별칭을 사용하지 마십시오.

    zero3232021-08-21 08:48:45

    외부 가입은 어떨까요? 일치가없는 모든 행은 테이블의 키 열 중 하나에 null을 가지지 만 미리 알지 못하는 시간을 미리 알지 못합니다. 그 사건을 우아하게 처리 할 수있는 방법이 있습니까?

    Darryl2021-08-21 08:48:45

    @Darryl 합력 및 두 드롭.

    zero3232021-08-21 08:48:45

    합류 된 데이터 프레임에서 열 이름을 입력 테이블의 열 이름 이외의 다른 것으로 원합니다. 이 일을 할 수있는 방법이 있습니까? 예 : "b"데이터 프레임에서 찍은 "foo"로 열 이름을 "foo"로 사용하는 대신 열 이름을 "column_new"로 사용하고 싶습니다. 이 SQL 쿼리와 같은 뭔가 : "column_new로 b.foo 선택"

    JKC2021-08-21 09:17:33
  • 답변 # 7

    단순히 사용할 수 있습니다

    df1.join(df2, Seq("ts","id"),"TYPE-OF-JOIN")
    

    여기에 가입 유형이 될 수 있습니다.

    • 왼쪽
    • right
    • 내부
    • 풀로우

    예를 들어 다음과 같은 두 개의 데이터 프레임이 있습니다.

    //df1
    word   count1
    w1     10
    w2     15
    w3     20
    //df2
    word   count2
    w1     100
    w2     150
    w5     200
    

    풀로우터 가입을 수행하면 결과가 다음과 같습니다.

    df1.join(df2, Seq("word"),"fullouter").show()
    word   count1  count2
    w1     10      100
    w2     15      150
    w3     20      null
    w5     null    200
    

    여기서 조건을 어떻게 추가합니까, col ( "count1")>10 say

    CpILL2021-08-21 17:27:09

    나는 당신이 df1.join (df2, seq ( "단어"), "풀로우"와 같은 일을 할 수 있다고 생각합니다. 필터 ($ "count1">10) .show (). 작동하지 않으면 알려주세요.

    Abu Shoeb2021-08-21 17:41:33

    Seq을 어떻게 수입합니까?

    bluesmonk2021-08-22 03:17:33
  • 답변 # 8

    SQL의 정상적인 동작은 다음과 같이 수행하고 있습니다.

    • 드롭 또는 원본 열의 이름 바꾸기
    • 가입
    • 라는
    • romed column

    여기에 "FullName"열을 대체하고 있습니다.

    자바의 일부 code :

    this
        .sqlContext
        .read()
        .parquet(String.format("hdfs:///user/blablacar/data/year=%d/month=%d/day=%d", year, month, day))
        .drop("fullname")
        .registerTempTable("data_original");
    this
        .sqlContext
        .read()
        .parquet(String.format("hdfs:///user/blablacar/data_v2/year=%d/month=%d/day=%d", year, month, day))
        .registerTempTable("data_v2");
     this
        .sqlContext
        .sql(etlQuery)
        .repartition(1)
        .write()
        .mode(SaveMode.Overwrite)
        .parquet(outputPath);
    

    여기서 쿼리가 다음과 같습니다.

    SELECT
        d.*,
       concat_ws('_', product_name, product_module, name) AS fullname
    FROM
        {table_source} d
    LEFT OUTER JOIN
        {table_updates} u ON u.id= d.id
    

    이것은 스파크만으로 할 수있는 것입니다. 나는 믿는 (목록에서 열을 삭제) 매우 유용합니다!

  • 답변 # 9

    단순한 답변 (에서)은 조인 된 열이 술어 대신 문자열 (또는 하나의 문자열)의

    아래의 원래 포스터의 질문에 답하기 위해 Databicks FAQ로 구성된 예제는 두 개의 조인 열과 함께 제공됩니다.

    여기 왼쪽 데이터 프레임이 있습니다.

    val llist= Seq(("bob", "b", "2015-01-13", 4), ("alice", "a", "2015-04-23",10))
    val left= llist.toDF("firstname","lastname","date","duration")
    left.show()
    /*
    +---------+--------+----------+--------+
    |firstname|lastname|      date|duration|
    +---------+--------+----------+--------+
    |      bob|       b|2015-01-13|       4|
    |    alice|       a|2015-04-23|      10|
    +---------+--------+----------+--------+
    */
    

    여기 오른쪽 데이터 프레임이 있습니다.

    val right= Seq(("alice", "a", 100),("bob", "b", 23)).toDF("firstname","lastname","upload")
    right.show()
    /*
    +---------+--------+------+
    |firstname|lastname|upload|
    +---------+--------+------+
    |    alice|       a|   100|
    |      bob|       b|    23|
    +---------+--------+------+
    */
    

    여기에 조인 열이 술어로 정의되는 잘못된 솔루션입니다.왼쪽 ( "firstname")=== 권리 ( "firstname") & & 왼쪽 ( "lastname")=== 권리 ( "lastname")...에

    잘못된 결과는 그 것입니다이름그리고열은 합류 된 데이터 프레임에 복제됩니다.

    left.join(right, left("firstname")===right("firstname") &
    &
                     left("lastname")===right("lastname")).show
    /*
    +---------+--------+----------+--------+---------+--------+------+
    |firstname|lastname|      date|duration|firstname|lastname|upload|
    +---------+--------+----------+--------+---------+--------+------+
    |      bob|       b|2015-01-13|       4|      bob|       b|    23|
    |    alice|       a|2015-04-23|      10|    alice|       a|   100|
    +---------+--------+----------+--------+---------+--------+------+
    */
    

    정확한 솔루션은 조인 열을 문자열 배열로 정의하는 것입니다.seq ( "firstname", "lastname")...에 출력 데이터 프레임에는 복제 된 열이 없습니다.

    left.join(right, Seq("firstname", "lastname")).show
    /*
    +---------+--------+----------+--------+------+
    |firstname|lastname|      date|duration|upload|
    +---------+--------+----------+--------+------+
    |      bob|       b|2015-01-13|       4|    23|
    |    alice|       a|2015-04-23|      10|   100|
    +---------+--------+----------+--------+------+
    */
    

  • 답변 # 10

    나는 이것을 잠시 동안 붙어 있었고, 최근에 나는 솔루션을 솔루션으로 생각해 냈습니다.

    A는 말합니다

    scala> val a= Seq(("a", 1), ("b", 2)).toDF("key", "vala")
    a: org.apache.spark.sql.DataFrame= [key: string, vala: int]
    scala> a.show
    +---+----+
    |key|vala|
    +---+----+
    |  a|   1|
    |  b|   2|
    +---+----+
    and
    scala> val b= Seq(("a", 1)).toDF("key", "valb")
    b: org.apache.spark.sql.DataFrame= [key: string, valb: int]
    scala> b.show
    +---+----+
    |key|valb|
    +---+----+
    |  a|   1|
    +---+----+
    

    및 데이터 프레임 A에서 값만 선택하려면이 작업을 수행 할 수 있습니다.

    scala> a.join(b, a("key")=== b("key"), "left").select(a.columns.map(a(_)) : _*).show
    +---+----+
    |key|vala|
    +---+----+
    |  a|   1|
    |  b|   2|
    +---+----+
    

  • 이전 F와 T 명령은 VIM에서 무엇을합니까?
  • 다음 database : MongoDB -중복 된 문서 및 필터 요소를 찾습니다