2016-07-25 21 views
8

我需要一個按某些鍵(=列名)進行分區的窗口函數,按另一個列名排序並返回排名靠前的x行。如何在Spark窗口函數中以降序使用orderby()?

這工作正常按升序排列:

def getTopX(df: DataFrame, top_x: String, top_key: String, top_value:String): DataFrame ={ 
    val top_keys: List[String] = top_key.split(", ").map(_.trim).toList 
    val w = Window.partitionBy(top_keys(1),top_keys.drop(1):_*) 
     .orderBy(top_value) 
    val rankCondition = "rn < "+top_x.toString 
    val dfTop = df.withColumn("rn",row_number().over(w)) 
     .where(rankCondition).drop("rn") 
    return dfTop 
} 

但是,當我嘗試將它在第4行更改爲orderBy(desc(top_value))orderBy(top_value.desc),我得到一個語法錯誤。這裏的正確語法是什麼?

+0

什麼是你得到錯誤信息? –

回答

16

orderBy有兩個版本,一個與字符串一起工作,另一個與Column對象(API)一起使用。您的代碼正在使用第一個版本,該版本不允許更改排序順序。您需要切換到列版本,然後調用desc方法,例如myCol.desc

現在,我們進入API設計領域。傳遞Column參數的好處是你有更多的靈活性,例如,你可以使用表達式等。如果你想維護一個接受字符串的API而不是Column,你需要將字符串轉換爲柱。有很多方法可以做到這一點,最簡單的方法是使用org.apache.spark.sql.functions.col(myColName)

全部放在一起,我們得到

.orderBy(org.apache.spark.sql.functions.col(top_value).desc) 
+0

.orderBy(org.apache.spark.sql.functions.col(top_value).desc()) – kecso

+0

括號在Scala中是不必要的。 – Sim

+0

哦......當然,我沒有事件檢查,問題中的代碼是scala,並且有scala標籤:)對不起 – kecso

相關問題