Добавление дополнительных свойств к функции: улучшение времени и итерации - PullRequest
0 голосов
/ 01 июня 2018

У меня есть функция, написанная на python, которая выполняет две процедуры:

  1. Предварительная обработка: считывание данных из массива и вычисление некоторых значений, которые позже понадобятся мне для предотвращения повторных вычислений
  2. Итерируйте и вычисляйте «сводку» данных на каждом этапе и используйте ее для решения задачи оптимизации.

Код выглядит следующим образом:

import numpy as np
def iterative_hessian(data, targets,
                            sketch_method, sketch_size, num_iters):
    '''
    Original problem is min 0.5*||Ax-b||_2^2
    iterative_hessian asks us to minimise 0.5*||S_Ax||_2^2 - <A^Tb, x> 
    for a summary of the data S_A
    '''

    A = data
    y = targets
    n,d = A.shape
    x0 = np.zeros(shape=(d,))
    m = int(sketch_size) # sketching dimension

    ATy = A.T@y
    covariance_mat = A.T.dot(A)

    for n_iter in range(int(num_iters)):
        S_A = m**(-0.5)*np.random.normal(size=(m, n))
        B = S_A.T.dot(S_A)
        z = ATy - covariance_mat@x0 + np.dot(S_A.T, np.dot(S_A,x0)) #
        x_new = np.linalg.solve(B,z)
        x0 = x_new  
    return np.ravel(x0)

На практике яне используйте строку S_A = m**(-0.5)*np.random.normal(size=(m, n)), но используйте другое случайное преобразование, которое применяется быстрее, но в принципе этого достаточно для вопроса.Этот код хорошо работает для того, что мне нужно, но мне было интересно, есть ли разумный способ сделать следующее:

  1. Вместо того, чтобы повторять строку S_A = m**(-0.5)*np.random.normal(size=(m, n)) для каждой итерации, есть ли способ указатьколичество независимых случайных копий (num_iters - которые можно считать между 10 и 30) из S_A, которые необходимы до итерации и сканируют входные данные только один раз, чтобы сгенерировать все такие копии?Я думаю, что в этом случае переменные S_A будут храниться в каком-то многомерном массиве, но я не уверен, как лучше это сделать, или даже практично ли это.Я попробовал базовый пример, делающий это параллельно, но он медленнее, чем многократно проходящий через матрицу.
  2. Предположим, что я хочу наделить эту функцию большим количеством свойств, например, я хочу вернуть среднее время, затраченное налиния x_new = np.linalg.solve(B,z).Сделать это просто - импортируйте модуль времени и поместите код в функцию, однако это всегда будет время функции, и, возможно, я хочу сделать это только при тестировании.Простой способ обойти это - создать параметр в определении функции time_updates = False и затем if time_updates == False: продолжить, как описано выше else:, скопировать точно такой же код, но с добавлением некоторой функциональности синхронизации.Есть ли лучший способ сделать это, который может использовать классы в Python?

Я собираюсь использовать эту итерацию для блоков данных, считываемых из файла, который не помещается в память.Хотя можно сохранить блок в памяти, было бы удобно, если бы функция проходила через этот блок только один раз, а не num_iters раз.Прохождение по вычисленным величинам, S_A, covariance_matrix и т. Д., Хорошо, однако.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...