訓練一個神經網絡每每只須要簡單的幾步:python
若是上述的每一個步驟都須要咱們寫Python的代碼去一步步實現,未免顯的繁瑣,好在MXNet提供了Module模塊來解決這個問題,Module把訓練和推理中一些經常使用到的步驟代碼進行了封裝。對於必定已經用Symbol定義好的神經網絡,咱們能夠很容易的使用Module提供的一些高層次接口或一些中間層次的接口來讓整個訓練或推理容易操做起來。api
下面咱們將經過在UCI letter recognition數據集上訓練一個多層感知機來講明Module模塊的用法。網絡
咱們先下載一個數據集,而後按80:20的比例劃分訓練集與測試集。咱們經過MXNet的IO模塊提供的數據迭代器每次返回一個batch size =32的訓練樣本dom
import logging logging.getLogger().setLevel(logging.INFO) import mxnet as mx import numpy as np # 數據以文本形式保存,每行一個樣本,每一行數據之間用','分割,每個字符爲label fname = mx.test_utils.download('http://archive.ics.uci.edu/ml/machine-learning-databases/letter-recognition/letter-recognition.data') data = np.genfromtxt(fname, delimiter=',')[:,1:] label = np.array([ord(l.split(',')[0])-ord('A') for l in open(fname, 'r')]) batch_size = 32 ntrain = int(data.shape[0]*0.8) train_iter = mx.io.NDArrayIter(data[:ntrain, :], label[:ntrain], batch_size, shuffle=True) val_iter = mx.io.NDArrayIter(data[ntrain:, :], label[ntrain:], batch_size)
net = mx.sym.var('data') net = mx.sym.FullyConnected(data=net, name='fc1', num_hidden=64) net = mx.sym.Activation(data=net, name='relu1', act_type='relu') net = mx.sym.FullyConnected(data=net, name='fc2', num_hidden=26) net = mx.sym.SoftmaxOutput(net, name='softmax') mx.viz.plot_network(net)
咱們能夠經過mx.mod.Module
接口建立一個Module對象,它接收下面幾個參數:ide
symbol
:神經網絡的定義context
:執行運算的設備data_names
:網絡輸入數據的列表label_names
:網絡輸入標籤的列表對於咱們在第二步定義的net,只有一個輸入數據即data,輸入標籤名爲softmax_label,這個是咱們在使用SoftmaxOutput操做時,自動命名的。測試
mod = mx.mod.Module(symbol=net, context=mx.cpu(), data_names=['data'], label_names=['softmax_label'])
中間層次的接口主要是爲了給開發者足夠的靈活性,也方便排查問題。咱們下面會先列出來Moduel模塊有哪些常見的中間層API,而後再利用這個API來訓練咱們剛纔定義的網絡。優化
bind
:綁定輸入數據的形狀,分配內存init_params
:初始化網絡參數init_optimizer
:指定優化方法,好比sgd
metric.create
:指定評價方法forward
:向前計算update_metric
:根據上一次的forward結果,更新評價指標backward
:反射傳播update
:根據優化方法和梯度更新模型的參數# allocate memory given the input data and label shapes mod.bind(data_shapes=train_iter.provide_data, label_shapes=train_iter.provide_label) # initialize parameters by uniform random numbers mod.init_params(initializer=mx.init.Uniform(scale=.1)) # use SGD with learning rate 0.1 to train mod.init_optimizer(optimizer='sgd', optimizer_params=(('learning_rate', 0.1), )) # use accuracy as the metric metric = mx.metric.create('acc') # train 5 epochs, i.e. going over the data iter one pass for epoch in range(5): train_iter.reset() metric.reset() for batch in train_iter: mod.forward(batch, is_train=True) # compute predictions mod.update_metric(metric, batch.label) # accumulate prediction accuracy mod.backward() # compute gradients mod.update() # update parameters print('Epoch %d, Training %s' % (epoch, metric.get()))
Moudle
模塊同時提供了高層次的API來完成訓練、預測和評估。不像使用中間層次API那樣繁瑣,咱們只須要一個接口fit
就能夠完成上面的步驟。設計
# reset train_iter to the beginning train_iter.reset() # create a module mod = mx.mod.Module(symbol=net, context=mx.cpu(), data_names=['data'], label_names=['softmax_label']) # fit the module mod.fit(train_iter, eval_data=val_iter, optimizer='sgd', optimizer_params={'learning_rate':0.1}, eval_metric='acc', num_epoch=8)
使用Moudle.predict
能夠獲得數據的predict的結果。若是咱們對結果不關心,咱們可使用score
接口直接計算驗證數據集的準確率。code
y = mod.predict(val_iter) score = mod.score(val_iter, ['acc']) print("Accuracy score is %f" % (score[0][1]))
上面的代碼中咱們使用了acc
來計算準確率,咱們還能夠設置其餘評估方法,如:top_k_acc
,F1
,RMSE
,MSE
,MAE
,ce
等。orm
咱們能夠經過設計一個checkpoint calback來在訓練過程當中每一個epoch結束後保存模型的參數
# construct a callback function to save checkpoints model_prefix = 'mx_mlp' checkpoint = mx.callback.do_checkpoint(model_prefix) mod = mx.mod.Module(symbol=net) mod.fit(train_iter, num_epoch=5, epoch_end_callback=checkpoint)
使用load_checkpoint
來加載已經保存的模型參數,隨後咱們能夠把這些參數加載到Moudle中
sym, arg_params, aux_params = mx.model.load_checkpoint(model_prefix, 3) # assign the loaded parameters to the module mod.set_params(arg_params, aux_params)
咱們也能夠不使用set_params
,而是直接在fit
接口中指定已經保存的checkpoint的參數,這些保存的參數會替代fit本來的參數初始化。
mod = mx.mod.Module(symbol=sym) mod.fit(train_iter, num_epoch=21, arg_params=arg_params, aux_params=aux_params, begin_epoch=3)