Повышение производительности функции Cython для более быстрого чтения файлов - PullRequest
2 голосов
/ 02 апреля 2019

Я пытаюсь прочитать файл ASCII (на основе текста) определенного формата.Я выполнил некоторое профилирование строки, и пост того времени используется в цикле.Я пытаюсь, если код внутри цикла может быть улучшена в производительности.

Вещи, которые я пробовал

  1. Более быстрая индексация массива numpy путем инициализации массива numpy с интерфейсом буфера, как в официальных документах , что я ожидалсильно ускорился, но с трудом справился.

  2. Пользовательская функция преобразования типов (без взаимодействия с питоном) для замены int (строка [0: 5]), но она закончилась довольно дорого

Пользовательская функция для преобразования типов

cdef int fast_atoi(str buf):
    cdef int i=0 ,c = 0, x = 0
    for i in range(5):
        c = buf[i]
        if c > 47 and c < 58:
            x = x * 10 + c - 48
    return x

Основной кодовый блок, который я хочу оптимизировать

def func(filename):
        cdef np.ndarray[np.int32_t] a1
        cdef np.ndarray[object] a2
        cdef np.ndarray[object] a3
        cdef np.ndarray[np.int32_t] a4
        cdef int count = 0
        cdef int n_lines
        cdef str line
        with open(filename) as inf:
            next(inf)
            n_lines = int(next(inf))
            a1 = np.zeros(n_atoms, dtype=np.int32)
            a2 = np.zeros(n_atoms, dtype=object)
            a3 = np.zeros(n_atoms, dtype = object)
            a4 =  np.zeros(n_atoms, dtype=np.int32)
            for i,line in enumerate(inf):
                if i == n_lines:
                    break
                try:
                    a1[i] =  int(line[0:5]) #custom function fast_atoi(line[0:5])
                    a2[i] = line[5:10].strip()
                    a3[i] = line[10:15].strip()
                    a4[i] = int(line[15:20])
                except (ValueError, TypeError) as e:
                    break

У меня 4.3mb file

Author
n_lines
    1xyz      A    1   5.202   4.356   3.155
    1mno     A1    2   5.119   4.411   3.172
    1mno     A2    3   5.155   4.283   3.104
    1nnn     B3    4   5.247   4.318   3.237
    1xax     KA    5   5.306   4.421   3.075
    1ooo     MA    6   5.383   4.347   3.054
    1cbd     NB    7   5.257   4.474   2.941
    1orc     OB1   8   5.189   4.404   2.893

Текущая реализация занимает в среднем 76 мс на моей машине. Добавление упомянутой пользовательской функции ухудшает ситуацию.

Буду очень признателен, если будут предложены некоторые улучшения.Я новичок в Cython.

...