theano: простая нейронная сеть с 6 слоями обучается со скоростью всего 132 точки данных в секунду. Почему это так медленно?

#openmp #gpu #nvidia #theano #hardware-acceleration

#openmp #графический процессор #nvidia #theano #аппаратное ускорение

Вопрос:

У меня довольно маленькая нейронная сеть с двумя полностью подключенными сигмовидными подсетями 10-> 100-> 10, выходные данные которых объединяются, а затем передаются в другую сеть 20-> 100-> 1. Эта архитектура довольно маленькая, имеет всего несколько весовых матриц, которые имеют максимальный размер 20×100 = 2000 весов.

Даже если я использую theano со всеми флагами, установленными для использования ускорения gpu, система достигает только 132 итераций (точек данных!) в секунду. Я не использую мини-пакеты, потому что это не ваша типичная нейронная сеть, а модель факторизации матрицы.

Система, которую я использую, имеет следующие характеристики:

ОС

 uname -a
Linux node081 2.6.32-358.18.1.el6.x86_64 #1 SMP Wed Aug 28 17:19:38 UTC 2013 x86_64 x86_64 x86_64 GNU/Linux
  

Программное обеспечение

  • Python 3.5.2 (скомпилирован мной)
  • theano 0.9.0dev2.dev-ee4c4e21b9e9037f2aa9626c3d779382840ea2e3
  • NumPy 1.11.2

процессор

 Intel(R) Xeon(R) CPU E5-2620 0 @ 2.00GHz
  

при nproc этом возвращается 12 , следовательно, может иметь 12 процессоров (или ядер?)

графический процессор

это результат nvidia-smi (при запущенном моем процессе):

  ------------------------------------------------------                 
| NVIDIA-SMI 5.319.49   Driver Version: 319.49         |                   
|------------------------------- ---------------------- ---------------------- 
| GPU  Name        Persistence-M| Bus-Id        Disp.A | Volatile Uncorr. ECC |
| Fan  Temp  Perf  Pwr:Usage/Cap|         Memory-Usage | GPU-Util  Compute M. |
|=============================== ====================== ======================|
|   0  Tesla K20m          On   | 0000:03:00.0     Off |                  Off |
| N/A   29C    P0    49W / 225W |       92MB /  5119MB |     19%      Default |
 ------------------------------- ---------------------- ---------------------- 

 ----------------------------------------------------------------------------- 
| Compute processes:                                               GPU Memory |
|  GPU       PID  Process name                                     Usage      |
|=============================================================================|
|    0      5903  python3                                               77MB  |
 ----------------------------------------------------------------------------- 
  

переменные команд и окружения

 OMP_NUM_THREADS=8 THEANO_FLAGS=mode=FAST_RUN,device=gpu,init_gpu_device=gpu,floatX=float32,nvcc.flags=-D_FORCE_INLINES,print_active_device=True,enable_initial_driver_test=True,warn_float64=raise,force_device=True,assert_no_cpu_op=raise python3 $@
  

настройки конфигурации theano, установленные во время выполнения

 theano.config.optimizer='fast_run'
theano.config.openmp=True
theano.config.openmp_elemwise_minsize=4
theano.config.floatX='float32'
theano.config.assert_no_cpu_op='raise'
  

Я также попытался отключить openmp, и он работает немного медленнее.

Кажется, я принял все меры предосторожности, чтобы убедиться, что у меня правильно настроено ускорение gpu. В чем может быть причина получения только 132 обновлений градиента каждую секунду? Есть ли какие-либо дополнительные проверки, которые мне нужно выполнить?

Ответ №1:

В theano,

  • Компиляция происходит намного быстрее optimizer=fast_compile , чем с optimizer=fast_run .
  • Используя новый сервер, с помощью нового оптимизатора, время компиляции в некоторых сетях увеличилось в 5 РАЗ. Я бы посоветовал вам всегда придерживаться нового бэкэнда. Вы можете использовать новый серверный сервер с помощью device=cuda flag .
  • Пока вы используете новый серверный интерфейс, я бы посоветовал вам использовать передовые технологии, если вам нужна скорость. Каждую неделю проводится множество оптимизаций, которые потенциально могут дать большие скорости.

  • Из документации вы можете установить флаг allow_gc=False , чтобы получить более высокую скорость

  • Вы можете установить флаг config.nvcc.fastmath равным True, если вам требуется некоторое ускорение операций деления и умножения за счет точности.
  • Если в вашей сети есть сверточные операции, вы можете установить некоторые config.dnn флаги в зависимости от вашей сети и потребностей. Также поможет установка флага cnmem.

  • Наконец, всякий раз, когда вы сообщаете, что код медленный, пожалуйста, поделитесь результатами профилирования, чтобы помочь разработке 🙂

Комментарии:

1. что я сделал, так это реструктурировал код, чтобы сделать возможными мини-пакеты. При размере мини-пакета 64 я получил ускорение примерно в 40 раз. Я мог бы попробовать ваши предложения рано или поздно.

2. Поскольку на графическом процессоре умножение матрицы на матрицу происходит намного быстрее, чем на матрицу -вектор, я предлагаю вам установить оптимальный размер мини-пакета, который позволит вам использовать почти всю память графического процессора, чтобы вы могли вычислять градиент быстрее и эффективнее

3. Правда, есть сложная проблема: размер мини-пакета также влияет на обучение: чем больше мини-пакет, тем меньше «стохастический» положительный эффект от стохастического градиентного спуска.