¿Cómo agregar filas en un dataframe de pandas en un bucle for?

Tengo lo siguiente para bucle:

for i in links: data = urllib2.urlopen(str(i)).read() data = json.loads(data) data = pd.DataFrame(data.items()) data = data.transpose() data.columns = data.iloc[0] data = data.drop(data.index[[0]]) 

Cada dataframe así creado tiene la mayoría de las columnas en común con las demás, pero no todas. Además, todos tienen una sola fila. Lo que necesito es agregar al dataframe todas las columnas distintas y cada fila de cada dataframe producido por el bucle for

Intenté pandas concatenadas o similares pero nada parecía funcionar. ¿Alguna idea? Gracias.

Supongamos que sus datos se parecen a esto:

 import pandas as pd import numpy as np np.random.seed(2015) df = pd.DataFrame([]) for i in range(5): data = dict(zip(np.random.choice(10, replace=False, size=5), np.random.randint(10, size=5))) data = pd.DataFrame(data.items()) data = data.transpose() data.columns = data.iloc[0] data = data.drop(data.index[[0]]) df = df.append(data) print('{}\n'.format(df)) # 0 0 1 2 3 4 5 6 7 8 9 # 1 6 NaN NaN 8 5 NaN NaN 7 0 NaN # 1 NaN 9 6 NaN 2 NaN 1 NaN NaN 2 # 1 NaN 2 2 1 2 NaN 1 NaN NaN NaN # 1 6 NaN 6 NaN 4 4 0 NaN NaN NaN # 1 NaN 9 NaN 9 NaN 7 1 9 NaN NaN 

Entonces podría ser reemplazado por

 np.random.seed(2015) data = [] for i in range(5): data.append(dict(zip(np.random.choice(10, replace=False, size=5), np.random.randint(10, size=5)))) df = pd.DataFrame(data) print(df) 

En otras palabras, no forme un nuevo DataFrame para cada fila. En su lugar, recopile todos los datos en una lista de dictados y, a continuación, llame a df = pd.DataFrame(data) una vez al final, fuera del bucle.

Cada llamada a df.append requiere la asignación de espacio para un nuevo DataFrame con una fila adicional, copiando todos los datos del DataFrame original en el nuevo DataFrame, y luego copiando los datos en la nueva fila. Toda esa asignación y copia hace que las llamadas df.append en un bucle sean muy ineficientes. El costo de tiempo de la copia crece de forma cuadrática con el número de filas. El código Call-DataFrame-once no solo es más fácil de escribir, sino que su rendimiento será mucho mejor: el costo del tiempo de copia aumenta linealmente con el número de filas.

Hay 2 razones por las que puede agregar filas en un bucle, 1. agregar a un df existente, y 2. crear un nuevo df.

para crear un nuevo df, creo que está bien documentado que debe crear sus datos como una lista y luego crear el dataframe:

 cols = ['c1', 'c2', 'c3'] lst = [] for a in range(2): lst.append([1, 2, 3]) df1 = pd.DataFrame(lst, columns=cols) df1 Out[3]: c1 c2 c3 0 1 2 3 1 1 2 3 

O BIEN, cree el dataframe con un índice y luego agréguelo

 cols = ['c1', 'c2', 'c3'] df2 = pd.DataFrame(columns=cols, index=range(2)) for a in range(2): df2.loc[a].c1 = 4 df2.loc[a].c2 = 5 df2.loc[a].c3 = 6 df2 Out[4]: c1 c2 c3 0 4 5 6 1 4 5 6 

Si desea agregar a un dataframe existente, puede usar cualquiera de los métodos anteriores y luego adjuntar los df juntos (con o sin el índice):

 df3 = df2.append(df1, ignore_index=True) df3 Out[6]: c1 c2 c3 0 4 5 6 1 4 5 6 2 1 2 3 3 1 2 3 

O, también puede crear una lista de entradas de diccionarios y agregarlas como en la respuesta anterior.

 lst_dict = [] for a in range(2): lst_dict.append({'c1':2, 'c2':2, 'c3': 3}) df4 = df1.append(lst_dict) df4 Out[7]: c1 c2 c3 0 1 2 3 1 1 2 3 0 2 2 3 1 2 2 3 

Usando el dict (zip (cols, vals)))

 lst_dict = [] for a in range(2): vals = [7, 8, 9] lst_dict.append(dict(zip(cols, vals))) df5 = df1.append(lst_dict) 

He creado un dataframe en un bucle for con la ayuda de un dataframe vacío temporal. Debido a que para cada iteración del bucle for, se creará un nuevo dataframe que sobrescribirá el contenido de la iteración anterior.

Por lo tanto, necesito mover el contenido del dataframe al dataframe vacío que ya se creó. Es tan simple como eso. Solo necesitamos usar la función .append como se muestra a continuación:

 temp_df = pd.DataFrame() #Temporary empty dataframe for sent in Sentences: New_df = pd.DataFrame({'words': sent.words}) #Creates a new dataframe and contains tokenized words of input sentences temp_df = temp_df.append(New_df, ignore_index=True) #Moving the contents of newly created dataframe to the temporary dataframe 

Fuera del bucle for, puede copiar el contenido del dataframe temporales en el dataframe maestros y luego eliminar el dataframe temporales si no lo necesita.

Una forma más compacta y eficiente sería quizás:

 cols = ['frame', 'count'] N = 4 dat = pd.DataFrame(columns = cols) for i in range(N): dat = dat.append({'frame': str(i), 'count':i},ignore_index=True) 

la salida sería:

 >>> dat frame count 0 0 0 1 1 1 2 2 2 3 3 3