as title 今天的主題是index和排序。
index是指欄與列的標籤系統,在運算、join/merge前,pandas會用索引標籤來做資料對齊。,資料對齊是什麼呢?就是欄位和索引會先進行配對以後再做運算。詳細等講到merge再來說。今天先focus在index上。
列索引:
dataframe.index
欄索引:
dataframe.columns
好的索引讓你上天堂,不好的索引就我思故我在了。
當兩個dataframe或series一起運算時,pandas會先做一個資料對齊的動作(語言癌啊),要是兩邊的欄位不一致就有可能因為迪卡兒乘積導致index爆炸。
資料可能會出現以下狀況,
所以最好的方式是確定索引唯一df.index.is_unique
不唯一怎麼辦,讓它唯一s1 = s1[~s1.index.duplicated(keep="first")]
keep的用法
s1 = pd.Series([1, 2, 6], index=["A", "A", "A"])
s2 = pd.Series([10, 20], index=["A", "A"])
print(s1 + s2)
s1 = s1[~s1.index.duplicated(keep="first")]
s2 = s2[~s2.index.duplicated(keep="first")]
print(s1 + s2)
還有另一種方法也可以讓它唯一df.reset_index(drop=True|False)
意思就是把重設index,改用位置型的RangeIndex取代
df = pd.DataFrame({"x":[1,2,3]}, index=["A","B","C"])
df = pd.DataFrame({"x":[1,2,3]}, index=["A","B","C"])
drop為true的結果:
row index | x |
---|---|
0 | 1 |
1 | 2 |
2 | 3 |
drop為false的結果:
row index | index | x |
---|---|---|
0 | A | 1 |
1 | B | 2 |
2 | C | 3 |
排序也是必備良藥,畢竟誰用excel沒用過排序呢~
排序分為
依欄位排序:df.sort_values(column,ascending=False)
# 單欄排序
df.sort_values("score")
# 多欄排序
df.sort_values(["score","age"], ascending=[False,True])
df.sort_values("score") # NaN 預設在最後
df.sort_values("score", na_position="first") # NaN 放前面
# 抓出分數最高的100筆, ascending為False是由大到小排序
df.sort_values("score", ascending=False).head(100)
# 抓出分數最低的100筆, ascending預設是True所以也可以不用賦值, 是由小到大排序
df.sort_values("score").head(100)
sort_values也常搭配drop_duplicates組合拳。
依列索引排序:df.sort_index(ascending=False)
df = pd.DataFrame({
"name":["Bojack","Dan","Todd"],
"score":[80,95,70]
}, index=[2,0,1])
print(df.sort_index()) # 預設升冪
print(df.sort_index(ascending=False)) # 降冪
雖然之前有講過了,但還是再帶一下,好用值得一提再提
nsmallest(count, 'column_name')
nlargest(count, 'column_name)
df["Model Year"].max()
df["Model Year"].idxmax()
df.loc[df["Model Year"].idxmax(), :]
df.select_dtypes(include="number").idxmax()
idmax是個很強大的function
好用到就離譜,只想說帥~好帥~
最小值就是把所有的max換成min,用min()、idxmin(),我就不再浪費it邦的空間複述了。
剛剛的sort_index,只要加個參數 axis=1,就可以做欄位名稱的排序了。
依欄位名稱排序:df.sort_index(axis=1, ascending=False)
但是這不符合實際應用場景啊。要以data有意義user要的方式排列,有以下幾種方法。
手排檔土法練鋼df = df[["a","b","c"]]
部分優先, 剩下接後面
first_cols = ["seq","name"]
df = df[first_cols + [col for col in df.columns if col not in first_cols]]
df = df[sorted(df.columns, key=lambda x: (len(x), x))]
frist = [c for c in df.columns if re.match("^x", c)]
left = [c for c in df.columns if c not in front]
df = df[frist + left]
好了,以上。打完收工,居然能在十一點前送出,真是太感人了。
下集預告:排序排完就來到分組groupby了!有可能一天講不完,畢竟書裡的第九章,它花了74頁才講完。沒關係不糾結,一天講不完就兩天。時到時擔當。