фильтровать строки с ошибкой преобразования dtype

#python #pandas #string #dtype

Вопрос:

У меня есть фрейм данных pandas с большим количеством столбцов. Тип dtype всех столбцов является объектом, поскольку некоторые столбцы имеют значения строк. Есть ли способ отфильтровать строки в другой фрейм данных, где значение в любом столбце является строкой, а затем преобразовать очищенный фрейм данных в целочисленный тип dtype.

Я разобрался во второй части, но не смог выполнить первую часть — отфильтровать строки, если значение содержит строковый символ, такой как «a», «b» и т. Д. например. если df является:

 df = pd.DataFrame({
    'col1':[1,2,'a',0,3],
    'col2':[1,2,3,4,5],
    'col3':[1,2,3,'45a5',4]
    })
 

Это должно стать 2 кадрами данных

 df = pd.DataFrame({
    'col1':[1,2,3],
    'col2':[1,2,5],
    'col3':[1,2,4]
    })

dfError = pd.DataFrame({
    'col1':['a',0],
    'col2':[3,4],
    'col3':[3,'45a5']
    })
 

Ответ №1:

Я считаю, что это эффективный способ сделать это.

 import pandas as pd

df = pd.DataFrame({ # main dataframe
    'col1':[1,2,'a',0,3],
    'col2':[1,2,3,4,5],
    'col3':[1,2,3,'45a5',4]
    }) 

mask = df.apply(pd.to_numeric, errors='coerce').isna() # checks if couldn't be numeric
mask = mask.any(1) # check rows that couldn't be numeric

df1 = df[~mask] # could be numeric
df2 = df[mask]  # couldn't be numeric
 

Сломать его:

 df.apply(pd.to_numeric) # converts the dataframe into numeric, but this would give us an error for the string elements (like 'a')

df.apply(pd.to_numeric, errors='coerce') # 'coerce' sets any non-valid element to NaN (converts the string elements to NaN).

>>>
   col1  col2  col3
0   1.0     1   1.0
1   2.0     2   2.0
2   NaN     3   3.0
3   0.0     4   NaN
4   3.0     5   4.0

mask.isna() # Detect missing values.
>>>
    col1   col2   col3
1  False  False  False
2   True  False  False
3  False  False   True
4  False  False  False

mask.any(1) # Returns whether any element is True along the rows
>>>
0    False
1    False
2     True
3     True
4    False
 

Комментарии:

1. Не могли бы вы объяснить, пожалуйста, что такое ошибки= «принуждение». Также я не знаю, что кто-нибудь делает.

2. Отредактировал andswer с объяснением. @fellowCoder

Ответ №2:

Не знаю, есть ли эффективный способ проверить это. Но грязный способ (может быть медленным) может быть:

 str_cond = df.applymap(lambda x: isinstance(x, str)).any(1)

df[~str_cond]
  col1  col2 col3
0    1     1    1
1    2     2    2
4    3     5    4

df[str_cond]
  col1  col2  col3
2    a     3     3
3    0     4  45a5
 

Комментарии:

1. Не могли бы вы, пожалуйста, объяснить, что происходит в лямбде и в любом другом.

2. applymap будет применен каждый элемент во фрейме данных с lambda указанием, где мы проверяем, соответствует ли элемент типу str . any(1) возвращает значение true, если какой-либо элемент в строке является строкой, которую мы можем в дальнейшем использовать для фильтрации фрейма данных.

3. Просто для подтверждения. «1» в любом случае представляет собой, если какой-либо один столбец. Если бы у меня там было «2», это означало бы любые 2 столбца. правильно? Кроме того, какова была бы ценность для всех?

4. Нет 1 представляет row , в то время 0 как представляет column собой . Поэтому, если вы поставите 1 туда, вы получите их в каждой строке, а если вы поставите 0 туда, вы получите их в каждом столбце. Я не думаю, что вы можете 2 туда положить.

5. понял! Спасибо!