Как я могу удалить строку с недопустимым значением?

#python #pandas #dataframe

#python #pandas #фрейм данных

Вопрос:

В наборе данных 16 недопустимых значений. Как я могу обнаружить и удалить строки с этими недопустимыми значениями? Имеет ли больше смысла означать или режим, а не удалять строку данных?

 import numpy as np
import seaborn as sns
import pandas as pd
import matplotlib.pyplot as plt
from pandas import read_csv
from sklearn.model_selection import train_test_split
from sklearn.model_selection import cross_val_score
from sklearn.model_selection import StratifiedKFold
from sklearn.metrics import classification_report
from sklearn.metrics import confusion_matrix
from sklearn.metrics import accuracy_score
from sklearn.tree import DecisionTreeClassifier
from sklearn.neighbors import KNeighborsClassifier
from sklearn.naive_bayes import GaussianNB

url = "https://raw.githubusercontent.com/genceremre/Datasets/master/breast-cancer-wisconsin.csv"
names = ['Clump Thickness', 'Cell-Size', 'Cell-Shape', 'Marginal-Adhesion', 
         'Single Epithelial Cell Size', 
         'Bare Nuclei', 'Bland Chromatin',
         'Normal Nucleoli', 'Mitoses', 'Class']
dataset = read_csv(url, names = names)

print(dataset.shape)
print(dataset.head(10))

print(dataset.describe())

print(dataset.groupby('Class').size())

num_missing = (dataset[0:]=='?').sum()
print(num_missing)
  

Ответ №1:

Похоже, у вас есть сочетание строк и числовых значений, например:

 import pandas as pd
df = pd.DataFrame({'col' : ['value 1', '1', -1, 0, 1, 2]})
df
Out[1]: 
       col
0  value 1
1        1
2       -1
3        0
4        1
5        2
  

Если вы это сделаете df.info() , то это вернет:

 <class 'pandas.core.frame.DataFrame'>
RangeIndex: 6 entries, 0 to 5
Data columns (total 1 columns):
 #   Column  Non-Null Count  Dtype 
---  ------  --------------  ----- 
 0   col     6 non-null      object
dtypes: object(1)
memory usage: 176.0  bytes
  

Как и ожидалось, это возвращает object тип данных, поскольку столбец содержит сочетание строк и числовых значений. Чтобы исправить это, вы можете сделать:

 import pandas as pd
df['col'] = pd.to_numeric(df['col'], errors='coerce')
Out[2]: 
   col
0  NaN
1  1.0
2 -1.0
3  0.0
4  1.0
5  2.0
  

Обратите внимание, что строка value 1 вернулась NaN , потому что мы передали errors='coerce' ; однако строка '1' была изменена на числовое значение 1 .

Важно отметить, что теперь вы можете фильтровать фрейм данных, потому что другой df.info() показывает, что pd.to_numeric изменилось Dtype на float64 . Следующая строка кода привела бы к упомянутой вами ошибке, но теперь этого не произойдет, поскольку Dtype является float64 :

 df = df[df['col'] > 0]
  

Вот полный код:

 In[3]:
        col
0   value 1
1   1
2   -1
3   0
4   1
5   2

import pandas as pd
df = pd.DataFrame({'col' : ['value 1', '1', -1, 0, 1, 2]})
df['col'] = pd.to_numeric(df['col'], errors='coerce')
df = df[df['col'] > 0]
df

Out[3]: 
   col
1  1.0
4  1.0
5  2.0
  

Вы также могли бы сделать:

 df = df[df['col'].notnull()]
  

чтобы вернуть все, кроме строк со NaN значениями, а не со значениями > 0. Очевидно, это зависит от того, что вы пытаетесь отфильтровать. В вашем случае ? было бы изменено на NaN при выполнении pd.to_numeric() и передаче errors=coerce .

Ответ №2:

Допустим, вы хотите удалить все строки с ‘размером ячейки’ ниже нуля. Это сделает это:

 dataset = dataset[dataset['Cell-Size'] > 0]
  

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

1. Моя проблема в столбце «Голые ядра». Я получаю сообщение об ошибке ‘>’ не поддерживается между экземплярами ‘str’ и ‘int’

2. И при каком условии вы хотели бы удалить строки?

3. Следуя предоставленному вами решению, я получил строку ошибки, и int не может быть сравнен. ‘Голые ядра’ == ‘?’ Можно ли удалить, выбрав содержащую строку?

4. @genceremre у вас есть строки в ваших столбцах. Вам нужно очистить это, прежде чем вы сможете выполнять векторизованную функцию для всего столбца, которая возвращает True для всех значений >0 .

Ответ №3:

Вот один из способов удалить все строки, содержащие определенное значение:

dataset = dataset[dataset.apply(lambda row: any(row != "?"), axis=1)]