跳到主要內容

Rust - Polars 資料欄位型態轉換,從 str 變 Date

緣起

Polars 是一個以 Rust 語言開發的 「DataFrame」 新興套件,它可以同時在 Rust 及 Python 中使用。Polars 憑藉著 Rust 的執行速度為基礎,讓它在資料處理的領域中, 逐漸流行起來。

但正由於它還在發展初期,目前網路上的參考文章相對較少,中文的內容更是稀有;所以整理了一下這週末的一些研究心得,一來避免自己忘記,二來也在網路上與大家分享,希望慢慢的能讓 Rust 的中文資源可以越來越完整,有朝一日可以在華人世界中流行起來。


本文開始

本週研究的主題是 Polars 裡,對「DataFrame」某個「str」欄位,進行資料型別轉換為「Date」或「Datetime」。資料的轉換可以有多種方式,應該不只限於接下來提到的方法。


建立第一個資料集

為了開始這個操作,我們需要先建立起一個「DataFrame」。


let date = Series::new("trans_date", &[
"2023-05-01",
"2023-05-02",
"2023-05-03",
"2023-05-04",
"2023-05-05",
]);

let df = DataFrame::new(vec![ date ]);
println!("{}", df.clone().collect()?);
 

執行後, 可以看到以下的結果:

 shape: (5, 1)
┌────────────┐
│ trans_date │
│ ---        │
│ str        │
╞════════════╡
│ 2023-05-01 │
│ 2023-05-02 │
│ 2023-05-03 │
│ 2023-05-04 │
│ 2023-05-05 │
└────────────┘

從執行的結果中,我們可以清楚的看到,目前所建立的「DataFrame」,在「trans_date」的欄位中,它的資料型態為「str」;也就是說,目前它是一個字串。如果我們只有操作到這裡,我想這樣的結果還不致於會有什麼太大的問題,反正只是把結果給顯示出來,頂多做個排序,大致上結果應該都會是正確的。

但如果我們想做的不只是這樣,需要對這個資料集進行一些更細緻的操作呢(例如,對這個資料進行過濾,找出早於/晚於某個日期的記錄)?這個時候,將原本的「str」型態轉換為「Date」型態,相信會是一個更好的選擇。


準備進行轉換

在開始進行轉換之前,我們要對上面的程式碼做一點小小的調整。Polars 的「DataFrame」操作模式有兩種,一為一般模式,二為「Lazy」模式。兩者最大的差別在於,一般模式在每一個功能呼叫時,當下就會對資料集進行操作;但「Lazy」模式則是在最終確認後,才一次執行所有的運算。「Lazy」模式讓我想到多年前學習 Big Data 時,使用 Apache Hadoop 及 Apache Spark,以及這幾年玩機器學習框架 TensorFlow 及 PyTorch 時,對資料集進行操作的方式,實在有異曲同工之妙。

在 Polars 官方的說明文件中,推薦我們使用「Lazy」模式,因此對程式做一些小小的調整:


let date = Series::new("trans_date", &[
"2023-05-01",
"2023-05-02",
"2023-05-03",
"2023-05-04",
"2023-05-05",
]);

let df = DataFrame::new(vec![ date ])?.lazy();

在上面的程式碼裡,紅色的「 .lazy() 」幫我們把原本的「DataFrame」,轉換為「LazyFrame」。在轉換操作模式後,我們透過下面的操作,要開始對資料集的「trans_date」欄,進行型別轉換:


// casting data type
let df = df.with_column(
col("trans_date").str().strptime(
DataType::Date,
StrptimeOptions {
format: Some("%Y/%m/%d".into()),
cache: false,
exact: false,
strict: false,
tz_aware: false,
utc: false,
},
)
);
 
println!("{}", df.clone().collect()?); 

「.with_column()」 用來為一個「DataFrame」加入一個欄位;過程裡,我們可以透過 Polars 裡的 Expression 描述,來對某一個欄位進行運算操作,並將結果存入這個欄位中。有一點比較特別的是,如果沒有特別再定義別名(alias),則運算後的結果,將會回填到原本指定的欄位中(在我們的例子裡,會寫入 「trans_date」 欄位)。我們即利用這個行為, 來為資料集的特定欄位,進行資料型別的轉換。

執行後,印出資料集的內容如下:

shape: (5, 1)
┌────────────┐
│ trans_date │
│ ---        │
│ date       │
╞════════════╡
│ 2023-05-01 │
│ 2023-05-02 │
│ 2023-05-03 │
│ 2023-05-04 │
│ 2023-05-05 │
└────────────┘

到這裡,我們可以清楚看到欄位的資料型態,已經從原本的「str」變更為「date」。

以下附上完整的程式碼:  

 
use polars::prelude::*;

fn main() -> PolarsResult<()> {
let date = Series::new(
"trans_date",
&[
"2023-05-01",
"2023-05-02",
"2023-05-03",
"2023-05-04",
"2023-05-05",
],
);

let price = Series::new("price", &[1, 2, 3, 4, 5]);

let df = DataFrame::new(vec![date])?.lazy();

// casting data type
let df = df.with_column(
col("trans_date").str().strptime(
DataType::Date,
StrptimeOptions {
format: Some("%Y-%m-%d".into()),
cache: false,
exact: false,
strict: false,
tz_aware: false,
utc: false,
},
));

println!("{}", df.clone().collect()?);

Ok(())
}

 


留言

這個網誌中的熱門文章

青山瀑布、老梅外拍

班上的第二次外拍,不過今天的狀況不大好,不太能抓到感覺,很多景都是看人家拍就跟著拍(除了那隻不知名的小蟲除外);到了老梅更慘,沒有減光鏡,只能夠拍出海浪拍打岩岸的畫面,平常看到人家拍老梅那種細細柔柔的味道,一點都沒辦法呈現。 不過我不覺得這次外拍是失敗的,至少我大概知道使用減光鏡能怎樣表現,也拍到了那張岩石上奇特的小蟲。 Ps. 文華大哥謝謝你啦!教我擺個葉子,讓畫面更有感覺。 :) Fig. 1 蠻有詩意的畫面,不過我覺得流水的型狀還不夠漂亮就是了。 Fig. 2 老師評語:在不是楓紅的季節,擺張綠色的葉子,清楚的五爪在畫面上顯的相當有張力。不過Fig1改採直幅構圖,感覺應該會更好。 Fig. 3 老師評語:只有黑與白,顏色比較單調。不過曝光控調的還不錯。 Fig. 4 流水澎湃你感覺到了嗎? 老師評語:同上一張,顏色單調;可以考慮用些植物做為前景來搭配。 Fig. 5 老師評語:綠葉沒有透光的感覺,看起來暗暗的;加上後方白色的瀑布,主體不明顯。 Fig. 6 老師評語:光影變化、曝光控制還不錯,下方的石頭可以考慮裁切掉,或著留更多成為前景。 Fig. 7 我很喜歡這張照片,不錯的光影變化,充滿生命力的感覺。 老師評語:特別的光影變化,還有生動昆蟲。雖然昆蟲的細節因顏色不明顯,不過和特別的光影變化搭配,加上石頭的曲線,乃是相當不錯。 Fig. 8 老師評語:沒有用減光鏡,所以石頭上有輕微的反光,顏色不夠生動。不過構圖上,使用石槽將視線由左下往右上引導至浪花,感覺還不錯。 Fig. 9 老梅奇特的岩岸地形。 老師評語:利用直幅構圖,表現石槽及延伸感。 Fig. 10 海水拍打在岩岸上,濺起陣陣的水花。 老師評語:快門速度要快不快、要慢不慢,可以再斟酌一下。 Fig. 11 老師評語:拍人物時沒有打閃光,導致眼睛有陰影而無神。可以透過閃光燈補光,製造眼神光。

翻滾吧…鯨鯨!!

翻滾吧…鯨鯨!! , a photo by 我是歐嚕嚕 (I'm Olulu...) on Flickr. Information: Camera: LOMO LC-A Film: Kodak EB3

20070901 - 八斗子夜潛

其實這篇應該很早就得貼出來了,可是這陣子實在忙的很,每天都得上課到晚才能回家。整理完了當天上課的內容,也差不多該睡了,實在沒有多餘的時間可以整理照片。 昨天利用了一點時間,加了些夜班,終於把它們整理完,貼出來和大家一塊分享。 #1. 剛從雲中升起的旭日,映照在平靜的海面上; #2. 海底花園裡的海扇,跟著水流的節奏,隨波飄逸; #3. 辛勤的海葵蝦,正忙碌的整理著海葵構起的家; #4. #5. #6. #7. 中國管口魚(好長的嘴巴); #8. 別太靠近我,我可是盯著你看喔~; #9. 熱鬧的珊瑚礁,就像繁忙的台北街頭; #10. 唔~躲起來,你看不到我! #11. 不一樣的海蛞蝓 #12. 成群結隊的甲香魚,就像動作伶俐的小精靈; #13. 獅子魚是花園的常客; #14. 只要有來,就能遇見牠; #15. 冒了被咬的危險,好不容易拍到的小蝦子; #16. 哇唔~你猜我在哪裡?