I'm learning about outlier detection and I wrote these two methods to get the row indexes of the instances that have outliers so I can drop them later. The problem is I'm getting two numbers very far from each other with these two methods.
I would like to know if interquartile range tends to identify more than zscore or maybe the code is wrong. The dataset I'm using is "Rain in Australia" and "att_num" is only the numerical attributes.
indexes = att_num.index
indexes_to_remove = set()
# interquartile range
indexes_to_remove.clear()
for name in att_num:
q1 = att_num[name].quantile(0.25)
q3 = att_num[name].quantile(0.75)
iqr = q3 - q1
x = 1.5 * iqr
lower_limit = q1 - x
upper_limit = q3 + x
condition = ((att_num[name] < lower_limit) | (att_num[name] > upper_limit))
indexes_to_remove.update(indexes[condition].tolist())
print("Lines to remove: {}.".format(len(indexes_to_remove)))
Lines to remove: 71176.
.
# z-score
indexes_to_remove.clear()
for name in att_num:
std_unit = 3
#scores = ((att_num[name] - att_num[name].mean()) / att_num[name].std())
scores = stats.zscore(att_num[name])
condition = ((scores < -std_unit) | (scores > std_unit))
indexes_to_remove.update(indexes[condition].tolist())
print("Lines to remove: {}".format(len(indexes_to_remove)))
Lines to remove: 6975