Pandas читает csv файл с поплавковыми значениями приводит к странным округлениям и десятичным цифрам

У меня есть файл csv, содержащий числовые значения, такие как 1524.449677. Всегда есть ровно шесть знаков после запятой.

Когда я импортирую файл csv (и другие столбцы) через pandas read_csv, столбец автоматически получает object типа данных. Моя проблема в том, что значения показаны как 2470.6911370000003 которые на самом деле должны быть 2470.691137. Или значение 2484.30691 показано как 2484.3069100000002.

Это похоже на проблему с типом данных. Я попытался явно read_csv тип данных при импорте через read_csv, dtype аргумент dtype как {'columnname': np.float64}. Тем не менее этот вопрос не исчез.

Как я могу получить значения, импортированные и показанные точно так же, как они есть в исходном файле csv?

Ответы

Ответ 1

В Pandas используется специальный конвертер dec 2 bin, который снижает точность в зависимости от скорости.

Передача float_precision='round_trip' в read_csv исправляет это.

Посетите эту страницу, чтобы узнать об этом подробнее.

После обработки ваших данных, если вы хотите сохранить их обратно в CSV файл, вы можете передать
float_format = "%.nf" соответствующему методу.

Полный пример:

import pandas as pd

df_in  = pd.read_csv(source_file, float_precision='round_trip')
df_out = ... # some processing of df_in
df_out.to_csv(target_file, float_format="%.3f") # for 3 decimal places

Ответ 2

Я понимаю, что это старый вопрос, но, возможно, это поможет кому-то еще:

У меня была похожая проблема, но я не мог использовать то же решение. К сожалению, опция float_precision существует только при использовании движка C, а не с движком python. Поэтому, если вам нужно использовать движок python по какой-то другой причине (например, потому что движок C не может работать с литералами регулярных выражений в качестве разделителей), этот маленький "трюк" сработал для меня:

В аргументах pd.read_csv определите dtype='str', а затем преобразуйте ваш фрейм данных в любой dtype, который вы хотите, например, df = df.astype('float64').

Немного взломать, но, похоже, работает. Если у кого-то есть какие-либо предложения о том, как решить эту проблему лучше, дайте мне знать.