Estoy trabajando con un archivo csv grande y la penúltima columna tiene una cadena de texto que quiero dividir por un delimitador específico. Me preguntaba si hay una manera simple de hacer esto usando pandas o python.
CustNum  CustomerName     ItemQty  Item   Seatblocks                 ItemExt
32363    McCartney, Paul      3     F04    2:218:10:4,6                   60
31316    Lennon, John        25     F01    1:13:36:1,12 1:13:37:1,13     300Quiero dividir por el espacio (' ')y luego los dos puntos (':')en la Seatblockscolumna, pero cada celda daría como resultado un número diferente de columnas. Tengo una función para reorganizar las columnas para que la Seatblockscolumna esté al final de la hoja, pero no estoy seguro de qué hacer a partir de ahí. Puedo hacerlo en Excel con la text-to-columnsfunción integrada y una macro rápida, pero mi conjunto de datos tiene demasiados registros para que Excel los maneje.
En última instancia, quiero tomar registros como los de John Lennon y crear varias líneas, con la información de cada conjunto de asientos en una línea separada.

Respuestas:
Esto divide los bloques de asiento por espacio y le da a cada uno su propia fila.
O, para dar a cada cadena separada por dos puntos en su propia columna:
Esto es un poco feo, pero tal vez alguien intervenga con una solución más bonita.
fuente
DataFramemuy rápidamente. En mi caso, ejecutar el código en una tabla de ~ 200M resultó en el uso de ~ 10G de memoria (+ intercambio ...).split(), porque simplementereduce()atravesar la columna funciona de maravilla. El problema puede estar enstack()...NameError: name 'Series' is not definedpara esto. de donde seSeriessupone que debe venir? EDITAR: no importa, debería serpandas.Seriesya que se refiere al artículo depandasfrom pandas import Seriespor conveniencia / brevedad.A diferencia de Dan, considero que su respuesta es bastante elegante ... pero desafortunadamente también es muy ineficiente. Entonces, dado que la pregunta menciona "un gran archivo csv" , permítame sugerirle que intente en un shell la solución de Dan:
... comparado con esta alternativa:
... y esto:
El segundo simplemente se abstiene de asignar la Serie 100 000, y esto es suficiente para hacerlo alrededor de 10 veces más rápido. Pero la tercera solución, que irónicamente desperdicia muchas llamadas a str.split () (se llama una vez por columna por fila, por lo que es tres veces más que para las otras dos soluciones), es aproximadamente 40 veces más rápida que la primera, porque incluso evita tener una instancia de las 100 000 listas. Y sí, ciertamente es un poco feo ...
EDITAR: esta respuesta sugiere cómo usar "to_list ()" y evitar la necesidad de una lambda. El resultado es algo como
que es incluso más eficiente que la tercera solución, y ciertamente mucho más elegante.
EDITAR: el aún más simple
también funciona y es casi tan eficiente.
EDITAR: aún más simple ! Y maneja NaNs (pero menos eficiente):
fuente
tolist()es perfecta. En mi caso, solo quería una de las piezas de datos en la lista y pude agregar directamente una sola columna a mi df existente usando .ix:df['newCol'] = pd.DataFrame(df.col.str.split().tolist()).ix[:,2]obect of type 'float' has no len()que era desconcertante, hasta que me di cuenta de que algunas de mis filas teníanNaNen ellas, en lugar de hacerlostr.Otra solución similar con el encadenamiento es el uso
reset_indexyrename:Si en la columna NO hay
NaNvalores, la solución más rápida es usar lalistcomprensión con elDataFrameconstructor:Pero si la columna contiene
NaNsolo funcionastr.splitcon el parámetroexpand=Trueque devuelveDataFrame( documentación ), y explica por qué es más lento:fuente
expand=Trueopción de trabajarpandas.DataFramesmientras se usa,.str.split()por ejemplo.Otro enfoque sería así:
fuente
También puede usar groupby () sin necesidad de unirse y apilar ().
Utilice los datos de ejemplo anteriores:
fuente
0 31316 Lennon, John 25 F01 300 1:13:36:1,12 Ay la siguiente línea0 31316 Lennon, John 25 F01 300 1:13:37:1,13 BEste parece un método mucho más fácil que los sugeridos en otras partes de este hilo.
dividir filas en el marco de datos de pandas
fuente