建立箭號物件

建立陣列、資料表、張量和其他所有箭號實體的食譜。

建立陣列

箭號會將資料保留在連續陣列中,並最佳化記憶體使用量和 SIMD 分析。在 Python 中,可以使用 Python 清單 (或一般的循序類型)、numpy 陣列和 pandas 系列,來建立 pyarrow.Array

import pyarrow as pa

array = pa.array([1, 2, 3, 4, 5])
print(array)
[
  1,
  2,
  3,
  4,
  5
]

陣列也可以提供 遮罩,用來指定應視為 null 的值。

import numpy as np

array = pa.array([1, 2, 3, 4, 5],
                 mask=np.array([True, False, True, False, True]))

print(array)
[
  null,
  2,
  null,
  4,
  null
]

根據 numpypandas 建立陣列時,箭號會利用最佳化程式碼路徑,該路徑仰賴 numpypandas 在內部以記憶體儲存資料的表示法。

import numpy as np
import pandas as pd

array_from_numpy = pa.array(np.arange(5))
array_from_pandas = pa.array(pd.Series([1, 2, 3, 4, 5]))

建立資料表

箭號在 pyarrow.Table 中支援表格資料:每一個欄位都由一個 pyarrow.ChunkedArray 表示,而資料表可以透過配對多個陣列與它們欄位的名稱來建立。

import pyarrow as pa

table = pa.table([
    pa.array([1, 2, 3, 4, 5]),
    pa.array(["a", "b", "c", "d", "e"]),
    pa.array([1.0, 2.0, 3.0, 4.0, 5.0])
], names=["col1", "col2", "col3"])

print(table)
pyarrow.Table
col1: int64
col2: string
col3: double
----
col1: [[1,2,3,4,5]]
col2: [["a","b","c","d","e"]]
col3: [[1,2,3,4,5]]

根據純粹類型建立資料表

箭號允許快速零複製產生 numpy 和 pandas 陣列與系列的 arrow 陣列,但也可以根據純粹 Python 結構建立箭號陣列和資料表。

函數 pyarrow.table() 允許根據各種輸入 (包括純粹 Python 物件) 建立資料表。

import pyarrow as pa

table = pa.table({
    "col1": [1, 2, 3, 4, 5],
    "col2": ["a", "b", "c", "d", "e"]
})

print(table)
pyarrow.Table
col1: int64
col2: string
----
col1: [[1,2,3,4,5]]
col2: [["a","b","c","d","e"]]

注意

字典中提供的所有值都將傳遞給 pyarrow.array() 以轉換成 Arrow 陣列,而且,在可行的情況下,它將受益於零複製行為。

pyarrow.Table.from_pylist() 方法允許從 Python 的列字典清單建立表格。如果未明確傳遞架構,則會推論類型。

import pyarrow as pa

table = pa.Table.from_pylist([
    {"col1": 1, "col2": "a"},
    {"col1": 2, "col2": "b"},
    {"col1": 3, "col2": "c"},
    {"col1": 4, "col2": "d"},
    {"col1": 5, "col2": "e"}
])

print(table)
pyarrow.Table
col1: int64
col2: string
----
col1: [[1,2,3,4,5]]
col2: [["a","b","c","d","e"]]

建立記錄批次

Arrow 中的大部分 I/O 作業都會在將批次資料傳送至目的地時發生。pyarrow.RecordBatch 是 Arrow 表示批次資料的方式。RecordBatch 可以視為表格的一區塊。

import pyarrow as pa

batch = pa.RecordBatch.from_arrays([
    pa.array([1, 3, 5, 7, 9]),
    pa.array([2, 4, 6, 8, 10])
], names=["odd", "even"])

可以使用 pyarrow.Table.from_batches() 將多個批次組合成一個表格。

second_batch = pa.RecordBatch.from_arrays([
    pa.array([11, 13, 15, 17, 19]),
    pa.array([12, 14, 16, 18, 20])
], names=["odd", "even"])

table = pa.Table.from_batches([batch, second_batch])
print(table)
pyarrow.Table
odd: int64
even: int64
----
odd: [[1,3,5,7,9],[11,13,15,17,19]]
even: [[2,4,6,8,10],[12,14,16,18,20]]

同樣地,pyarrow.Table 可以使用 pyarrow.Table.to_batches() 方法,轉換成 pyarrow.RecordBatch 的清單。

record_batches = table.to_batches(max_chunksize=5)
print(len(record_batches))
2

儲存類別資料

Arrow 提供 pyarrow.DictionaryArray 類型,可以表示類別資料,並不會因為重複儲存和重複類別,而付出代價。當欄位可能包含大量的儲存值 (如文字) 時,這可以減少記憶體用量。

如果您有一個包含重複類別資料的陣列,則可以使用 pyarrow.DictionaryArray 將其轉換成 pyarrow.Array.dictionary_encode()

arr = pa.array(["red", "green", "blue", "blue", "green", "red"])

categorical = arr.dictionary_encode()
print(categorical)
...
-- dictionary:
  [
    "red",
    "green",
    "blue"
  ]
-- indices:
  [
    0,
    1,
    2,
    2,
    1,
    0
  ]

如果您已知類別和索引,則可以略過編碼步驟,直接使用 pyarrow.DictionaryArray.from_arrays() 建立 DictionaryArray

categorical = pa.DictionaryArray.from_arrays(
    indices=[0, 1, 2, 2, 1, 0],
    dictionary=["red", "green", "blue"]
)
print(categorical)
...
-- dictionary:
  [
    "red",
    "green",
    "blue"
  ]
-- indices:
  [
    0,
    1,
    2,
    2,
    1,
    0
  ]