Я пытаюсь сократить время, необходимое для применения сложной функции из библиотеки cantools к каждой строке в кадре данных (до 2 миллионов строк):
Timestamp Type ID Data
0 16T122109957 0 522 b'0006'
1 16T122109960 0 281 b'0000ce52d2290000'
2 16T122109960 0 279 b'0000000000000000'
3 16T122109960 0 304 b'0000'
4 16T122109961 0 277 b'400000'
Использование приведенного выше кадра данных и дБ c файл считан. Файл DB c представляет собой набор правил кодирования / декодирования данных.
Использование DataFrame может занять до 10 минут:
df['decoded'] = df.apply(lambda x: dbc.decode_message(df['ID'][x], df['Data']))
Помещение двух столбцов в списки и последующая итерация по спискам занимает всего около минуты, но когда новый массив сохраняется в кадре данных, появляется ошибка ValueError: array is too big
. Что ожидается, так как это ОГРОМНО.
Пример l oop код:
id_list = df['ID'].tolist()
datalist = df['Data'].tolist()
for i in range(len(id_list)):
listOfDicts.append(dbc.decode_message(id_list[i], datalist[i]))
Data = DataFrame(listOfDicts)
Я попытался python векторизация, которая, по-видимому, самая быстрая и была встречена с ошибкой TypeError: 'Series' objects are mutable, thus they cannot be hashed
который я не могу исправить. пример:
Data['dict'] = dbc.decode_message(df['ID'], df['Data'])
Есть ли другие способы ускорить процесс применения или мне следует попробовать работать над векторизацией?
МИНИМАЛЬНЫЙ пример:
import cantools
import pandas as pd
df = pd.read_csv('file.log', skiprows=11, sep=';')
dbc = cantools.database.load_file('file.dbc')
# option 1 SLOW
df['decoded'] = df.apply(lambda x: dbc.decode_message(x['ID'], x['Data']))
# option 2 Faster...
id_list = df['ID'].tolist()
datalist = df['Data'].tolist()
for i in range(len(id_list)):
listOfDicts.append(dbc.decode_message(id_list[i], datalist[i]))
Data = DataFrame(listOfDicts) #< -- causes error for being to big
#option 3
df['dict'] = dbc.decode_message(df['ID'], df['Data']) #< --Error