У меня есть файлы двоичных данных в диапазоне нескольких ГБ, которые я отображаю в памяти с помощью numpy. Начало каждого пакета данных содержит метку времени BCD. Где каждое шестнадцатеричное число закодировано в формате времени 0DDD: HH: MM: SS.ssss Мне нужно, чтобы эта метка времени была превращена в общее количество секунд текущего года.
![Data Excerpt](https://i.stack.imgur.com/zDQM6.png)
Пример:
Первая отметка времени 0x0261 1511 2604 6002
будет: 261: 15: 11: 26.046002 или
261*86400 + 15*3600 + 11*60 + 26.046002 = 22551986.046002
В настоящее время я делаю это, чтобы вычислить временные метки:
import numpy as np
rawData = np.memmap('dataFile.bin',dtype='u1',mode='r')
#findFrameStart returns the index to the start of each data packet [0,384,768,...]
fidx = findFrameStart(rawData)
# Do lots of bit shifting and multiplying and type casting....
day1 = ((rawData[fidx ]>>4)*10 + (rawData[fidx ]&0x0F)).astype('f8')
day2 = ((rawData[fidx+1]>>4)*10 + (rawData[fidx+1]&0x0F)).astype('f8')
hour = ((rawData[fidx+2]>>4)*10 + (rawData[fidx+2]&0x0F)).astype('f8')
mins = ((rawData[fidx+3]>>4)*10 + (rawData[fidx+3]&0x0F)).astype('f8')
sec1 = ((rawData[fidx+4]>>4)*10 + (rawData[fidx+4]&0x0F)).astype('f8')
sec2 = ((rawData[fidx+5]>>4)*10 + (rawData[fidx+5]&0x0F)).astype('f8')
sec3 = ((rawData[fidx+6]>>4)*10 + (rawData[fidx+6]&0x0F)).astype('f8')
sec4 = ((rawData[fidx+7]>>4)*10 + (rawData[fidx+7]&0x0F)).astype('f8')
time = (day1*100+day2)*86400 + hour*3600 + mins*60 + sec1 + sec2/100 + sec3/10000 + sec4/1000000
Обратите внимание, что мне пришлось разыграть каждую из промежуточных переменных (день1, день2 и т. Д.), Чтобы удвоить, чтобы time
вычислил правильно.
Учитывая, что существует много кадров, fidx
может быть довольно большим (~ 10e6 элементов или более). Это приводит к множеству математических операций, сдвигов битов, приведению и т. Д. В моем текущем методе. Пока что он работает нормально для меньшего тестового файла (~ 180 мс для файла данных 150 МБ). Тем не менее, я беспокоюсь о том, что при получении больших данных (4-5 ГБ) могут возникнуть проблемы с памятью для всех промежуточных массивов.
Поэтому, если возможно, я искал другой метод, который мог бы сократить некоторые накладные расходы. Операции от двоично-десятичного к десятичному аналогичны для каждого байта, поэтому, возможно, я должен быть в состоянии что-то перебрать и, возможно, преобразовать массив на месте ... по крайней мере, уменьшив объем памяти.
Буду признателен за любую помощь. К вашему сведению, я использую Python 3.7