Tworzenie ramki danych pandy wypełnionej zerami


105

Jaki jest najlepszy sposób na utworzenie ramki danych pandy wypełnionej zerami o danym rozmiarze?

Używałem:

zero_data = np.zeros(shape=(len(data),len(feature_list)))
d = pd.DataFrame(zero_data, columns=feature_list)

Czy jest lepszy sposób, aby to zrobić?


1
Nie, nie przychodzi mi do głowy żadna istotna poprawa.
— Dan Allan,

Otrzymuję błąd pamięci na np.zeros, ponieważ dane to duży zestaw. Jakieś wskazówki, co mogę zrobić? Nie mam żadnego innego wyjścia poza „MemoryError”. Mam 100 GB pamięci RAM, a dane mają tylko 20 GB, ale nadal zawodzą. Nie mam pojęcia, jak to debugować, 64-bitowy serwer Ubuntu. Trochę googlowałem, ale wszyscy mówią - podziel na kawałki, ale tych danych nie można podzielić.
— niedakh

Czy możesz po prostu pracować data? Dlaczego musisz stworzyć inną strukturę, aby ją utrzymać?
— Phillip Cloud,

Odpowiedzi:


144

Możesz spróbować tego:

d = pd.DataFrame(0, index=np.arange(len(data)), columns=feature_list)

2
Testowanie tego, co znalazłem, %timeit temp = np.zeros((10, 11)); d = pd.DataFrame(temp, columns = ['col1', 'col2',...'col11'])zajmuje 156 nas. Ale %timeit d = pd.DataFrame(0, index = np.arange(10), columns = ['col1', 'col2',...'col11'])zabiera nam 171. Dziwię się, że nie jest szybciej.
— emschorsch

3
Zauważ, że możesz napotkać problem z int / float, jeśli d.set_value(params)po zainicjowaniu będziesz robił coś takiego, daby zawierało 0. Łatwo naprawić to: d = pd.DataFrame(0.0, index=np.arange(len(data)), columns=feature_list).
— ximiki

31

Moim zdaniem najlepiej zrobić to z numpy

import numpy as np
import pandas as pd
d = pd.DataFrame(np.zeros((N_rows, N_cols)))

1
Kiedy zrobiłem to w ten sposób, nie mogłem zmienić wartości „0”. TypeError: 'numpy.float64' object does not support item assignment
— RightmireM

@RightmireM Jak dokładnie próbujesz je zmienić? Masz rację, typ danych tonp.float64
— AlexG

11

Podobny do @Shravan, ale bez użycia numpy:

  height = 10
  width = 20
  df_0 = pd.DataFrame(0, index=range(height), columns=range(width))

Wtedy możesz z nim zrobić, co chcesz:

post_instantiation_fcn = lambda x: str(x)
df_ready_for_whatever = df_0.applymap(post_instantiation_fcn)

8

Jeśli chcesz, aby nowa ramka danych miała ten sam indeks i kolumny, co istniejąca ramka danych, możesz po prostu pomnożyć istniejącą ramkę danych przez zero:

df_zeros = df * 0

2
Należy pamiętać, że wszędzie tam, gdzie df zawiera NaN, zamiast zer otrzymasz NaN.
— kadee

1

Jeśli masz już ramkę danych, jest to najszybszy sposób:

In [1]: columns = ["col{}".format(i) for i in range(10)]
In [2]: orig_df = pd.DataFrame(np.ones((10, 10)), columns=columns)
In [3]: %timeit d = pd.DataFrame(np.zeros_like(orig_df), index=orig_df.index, columns=orig_df.columns)
10000 loops, best of 3: 60.2 µs per loop

Porównać do:

In [4]: %timeit d = pd.DataFrame(0, index = np.arange(10), columns=columns)
10000 loops, best of 3: 110 µs per loop

In [5]: temp = np.zeros((10, 10))
In [6]: %timeit d = pd.DataFrame(temp, columns=columns)
10000 loops, best of 3: 95.7 µs per loop

1

Zakładając, że mamy szablon DataFrame, który chciałoby się skopiować z zerowymi wartościami wypełnionymi tutaj ...

Jeśli w zestawie danych nie ma żadnych NaN, pomnożenie przez zero może być znacznie szybsze:

In [19]: columns = ["col{}".format(i) for i in xrange(3000)]                                                                                       

In [20]: indices = xrange(2000)

In [21]: orig_df = pd.DataFrame(42.0, index=indices, columns=columns)

In [22]: %timeit d = pd.DataFrame(np.zeros_like(orig_df), index=orig_df.index, columns=orig_df.columns)
100 loops, best of 3: 12.6 ms per loop

In [23]: %timeit d = orig_df * 0.0
100 loops, best of 3: 7.17 ms per loop

Ulepszenie zależy od rozmiaru DataFrame, ale nigdy nie było wolniej.

I po prostu do cholery:

In [24]: %timeit d = orig_df * 0.0 + 1.0
100 loops, best of 3: 13.6 ms per loop

In [25]: %timeit d = pd.eval('orig_df * 0.0 + 1.0')
100 loops, best of 3: 8.36 ms per loop

Ale:

In [24]: %timeit d = orig_df.copy()
10 loops, best of 3: 24 ms per loop

EDYTOWAĆ!!!

Zakładając, że masz ramkę wykorzystującą float64, będzie to najszybsze z ogromnym marginesem! Jest również w stanie wygenerować dowolną wartość, zastępując 0,0 na żądany numer wypełnienia.

In [23]: %timeit d = pd.eval('orig_df > 1.7976931348623157e+308 + 0.0')
100 loops, best of 3: 3.68 ms per loop

W zależności od gustu można zdefiniować zewnętrznie nan i zrobić ogólne rozwiązanie, niezależnie od konkretnego typu spławika:

In [39]: nan = np.nan
In [40]: %timeit d = pd.eval('orig_df > nan + 0.0')
100 loops, best of 3: 4.39 ms per loop

1
Jest to zdecydowanie najbardziej wyczerpująca odpowiedź na czas, chociaż w przypadku PO wydaje się, że problemem były wymagania pamięci, a nie szybkość ... Nawiasem mówiąc, w moim systemie dwie pierwsze sugestie, które napisałeś, dają ten sam czas (Pandy 0.20.3 ), więc być może nastąpiły pewne zmiany.
— Moot
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.