Hentikan penggunaan values
dan as_matrix()
!
pandas v0.24.0 memperkenalkan dua metode baru untuk mendapatkan array NumPy dari objek panda:
to_numpy()
, yang didefinisikan pada Index
, Series,
dan DataFrame
objek, dan
array
, yang didefinisikan Index
dan Series
hanya objek.
Jika Anda mengunjungi v0.24 docs for .values
, Anda akan melihat peringatan merah besar yang mengatakan:
Peringatan: Sebaiknya gunakan DataFrame.to_numpy()
.
Lihat bagian ini dari catatan rilis v0.24.0 , dan jawaban ini untuk informasi lebih lanjut.
Menuju Konsistensi Yang Lebih Baik: to_numpy()
Dalam semangat konsistensi yang lebih baik di seluruh API, metode baru to_numpy
telah diperkenalkan untuk mengekstrak array NumPy yang mendasarinya dari DataFrames.
# Setup.
df = pd.DataFrame({'A': [1, 2, 3], 'B': [4, 5, 6]}, index=['a', 'b', 'c'])
df.to_numpy()
array([[1, 4],
[2, 5],
[3, 6]])
Seperti disebutkan di atas, metode ini juga didefinisikan Index
dan Series
objek (lihat di sini ).
df.index.to_numpy()
# array(['a', 'b', 'c'], dtype=object)
df['A'].to_numpy()
# array([1, 2, 3])
Secara default, tampilan dikembalikan, sehingga setiap modifikasi yang dilakukan akan memengaruhi yang asli.
v = df.to_numpy()
v[0, 0] = -1
df
A B
a -1 4
b 2 5
c 3 6
Jika Anda membutuhkan salinan, gunakan to_numpy(copy=True
).
panda> = 1.0 pembaruan untuk ExtensionTypes
Jika Anda menggunakan panda 1.x, kemungkinan Anda akan lebih sering berurusan dengan tipe ekstensi. Anda harus sedikit lebih berhati-hati agar jenis ekstensi ini dikonversi dengan benar.
a = pd.array([1, 2, None], dtype="Int64")
a
<IntegerArray>
[1, 2, <NA>]
Length: 3, dtype: Int64
# Wrong
a.to_numpy()
# array([1, 2, <NA>], dtype=object) # yuck, objects
# Right
a.to_numpy(dtype='float', na_value=np.nan)
# array([ 1., 2., nan])
Ini disebut dalam dokumen .
Jika Anda membutuhkan dtypes
...
Seperti yang ditunjukkan dalam jawaban lain, DataFrame.to_records
adalah cara yang baik untuk melakukan ini.
df.to_records()
# rec.array([('a', -1, 4), ('b', 2, 5), ('c', 3, 6)],
# dtype=[('index', 'O'), ('A', '<i8'), ('B', '<i8')])
to_numpy
Sayangnya, ini tidak bisa dilakukan . Namun, sebagai alternatif, Anda dapat menggunakan np.rec.fromrecords
:
v = df.reset_index()
np.rec.fromrecords(v, names=v.columns.tolist())
# rec.array([('a', -1, 4), ('b', 2, 5), ('c', 3, 6)],
# dtype=[('index', '<U1'), ('A', '<i8'), ('B', '<i8')])
Dari segi kinerja, hampir sama (sebenarnya, menggunakan rec.fromrecords
sedikit lebih cepat).
df2 = pd.concat([df] * 10000)
%timeit df2.to_records()
%%timeit
v = df2.reset_index()
np.rec.fromrecords(v, names=v.columns.tolist())
11.1 ms ± 557 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
9.67 ms ± 126 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
Dasar Pemikiran untuk Menambahkan Metode Baru
to_numpy()
(selain array
) ditambahkan sebagai hasil dari diskusi di bawah dua masalah GitHub GH19954 dan GH23623 .
Secara khusus, dokumen menyebutkan alasannya:
[...] dengan .values
itu tidak jelas apakah nilai yang dikembalikan akan menjadi array yang sebenarnya, beberapa transformasi, atau salah satu array kustom panda (seperti Categorical
). Misalnya, dengan PeriodIndex
, .values
menghasilkan ndarray
objek periode baru setiap kali. [...]
to_numpy
bertujuan untuk meningkatkan konsistensi API, yang merupakan langkah besar ke arah yang benar. .values
tidak akan ditinggalkan dalam versi saat ini, tetapi saya berharap ini dapat terjadi di beberapa titik di masa depan, jadi saya akan mendorong pengguna untuk bermigrasi ke API yang lebih baru, secepat Anda bisa.
Kritik atas Solusi Lain
DataFrame.values
memiliki perilaku yang tidak konsisten, sebagaimana telah dicatat.
DataFrame.get_values()
hanyalah pembungkus DataFrame.values
, jadi semua yang dikatakan di atas berlaku.
DataFrame.as_matrix()
sudah usang sekarang, JANGAN gunakan!