รวมหลาย dataframes ที่ส่งออกผ่านฟังก์ชัน FOR loop ให้เป็น dataframe เดียว

ฉันมีฟังก์ชัน FOR loop ที่วนซ้ำรายการตารางและคอลัมน์ (zip) เพื่อรับค่าต่ำสุดและสูงสุด เอาต์พุตจะถูกแยกออกจากกันสำหรับแต่ละชุดค่าผสม แทนที่จะเป็นหนึ่งดาต้าเฟรม/ตารางเดียว มีวิธีรวมผลลัพธ์ของ FOR loop ให้เป็นเอาต์พุตสุดท้ายภายในฟังก์ชันหรือไม่?

from pyspark.sql import functions as f

def minmax(tables, cols):
    for table, column in zip(tables, cols):
        minmax = spark.table(table).where(col(column).isNotNull()).select(f.lit(table).alias("table"), f.lit(column).alias("col"), min(col(column)).alias("min"), 
        max(col(column)).alias("max"))
        minmax.show()
tables = ["sales_123", "sales_REW"]
cols = ["costs", "price"]

minmax(tables, cols)

เอาท์พุตจากฟังก์ชัน:

+---------+-----+---+---+
|    table|  col|min|max|
+---------+-----+---+---+
|sales_123|costs|  0|400|
+---------+-----+---+---+

+----------+-----+---+---+
|     table|  col|min|max|
+----------+-----+---+---+
|sales_REW |price|  0|400|
+----------+-----+---+---+

ผลลัพธ์ที่ต้องการ:

+---------+-----+---+---+
|    table|  col|min|max|
+---------+-----+---+---+
|sales_123|costs|  0|400|
|sales_REW|price|  0|400|
+---------+-----+---+---+

person thecoder    schedule 05.05.2019    source แหล่งที่มา


คำตอบ (1)


ใส่ดาต้าเฟรมทั้งหมดลงในรายการและทำการรวมหลังจาก for-loop:

from functools import reduce
from pyspark.sql import functions as f
from pyspark.sql import DataFrame

def minmax(tables, cols):

    dfs = []        
    for table, column in zip(tables, cols):
        minmax = spark.table(table).where(col(column).isNotNull()).select(f.lit(table).alias("table"), f.lit(column).alias("col"), min(col(column)).alias("min"), max(col(column)).alias("max"))
        dfs.append(minmax)
    df = reduce(DataFrame.union, dfs)

โปรดทราบว่าลำดับของคอลัมน์จะต้องเหมือนกันกับดาต้าเฟรมที่เกี่ยวข้องทั้งหมด (ดังที่เป็นในกรณีนี้) มิฉะนั้นอาจให้ผลลัพธ์ที่ไม่คาดคิดได้

person Shaido    schedule 05.05.2019
comment
@Shaido ฉันจะเตรียมตารางและคอลัมน์เพื่อทดสอบโค้ดได้อย่างไร - person PIG; 05.05.2019
comment
@PIG: หากคุณเพียงต้องการทดสอบคุณสามารถสร้างรายการ Spark dataframes (อ่านจาก csvs หรือสร้างบางส่วนจาก pandas dataframes: stackoverflow.com/questions/43751509/) จากนั้นวนซ้ำสิ่งเหล่านั้น - person Shaido; 06.05.2019
comment
@Shaido ฉันกำลังพยายามผ่าน minmax(df1, cols) โดยที่ df1 คือ spark dataframe & cols = df1.columns ของฉัน มันบอกว่าคอลัมน์ไม่สามารถทำซ้ำได้ - person Abhi; 07.04.2021
comment
@Abhi: หากคุณมี dataframe เพียงอันเดียวคุณไม่ควรใช้วิธีแก้ปัญหาข้างต้น อย่างไรก็ตาม สิ่งที่คุณต้องการทำจะแตกต่างกันมากขึ้นอยู่กับสิ่งที่คุณต้องการทำจริงๆ อาจเป็นเช่น: stackoverflow.com/questions/60534796/ หรือ stackoverflow.com/questions/45382329/ - person Shaido; 07.04.2021
comment
@ไชโด ใช่แล้ว! วิ่งง่ายๆ df.select(*[f.mean(c).alias(c) for c in df.columns]) คุณช่วยเรื่องเปอร์เซ็นไทล์ได้ไหม ฉันมีคอลัมน์ ID (ไม่ซ้ำกัน), คอลัมน์หมวดหมู่ (ค่าที่แตกต่างกัน 5 ค่า), คอลัมน์ตัวเลข 5 คอลัมน์ เปอร์เซ็นต์ไทล์ - ต้องใช้ 25%, 50%, 75%, 100% สำหรับแต่ละคอลัมน์ตัวเลข จะรันวนซ้ำทั้ง 5 หมวดหมู่ - person Abhi; 07.04.2021