maandag 18 mei 2015

Tweede deel in DL met Python cursus


Waar het in het eerste deel nog ging om 'fake data' gaan we nu met echte gegevens werken. Een dataset van 60.000 getallen (0 .. 9) om deze te leren lezen. Tevens is er een aparte testset bij beschikbaar. Allemaal op de 'Mnist database'.  De dataset bestaat uit 60k plaatjes van 28 bij 28 pixels. Voor 'het gemak' zijn de nummers op de afbeeldingen allemaal even groot gemaakt en gecentraliseerd.
Het programma heet '2_log_reg.py' en is ook redelijk kort (totdat ik het weer visueel probeer te maken ;-) maar blijft op verschillende punten lastig te begrijpen. De structuur lijkt gelukkig op het eerste voorbeeld. Het krachtige van Python (en Theano) lijkt dat ondermeer met functies bewerkingen kunnen worden uitgevoerd op multidimensionale matrixes van verschillende (variabele) formaten. Zo maakt het de functie 'init_weights' niet uit hoe groot het array is dat wordt doorgegeven in 'shape'. Alle 'vakjes' worden daar voorzien van een (heel kleine) random waarde.  
Na FloatX, om het juiste datatype te kunnen maken en de zojuist besproken 'init_weights' hebben we weer de model definitie. T.dot vermenigvuldigd de matrixes X en w waarna 'softmax' een grootste uitkomst terug lijkt te geven. Dit deel is mij nog niet zo heel duidelijk.
Met een aanroep aan mnist worden de gegevens in het programma beschikbaar gemaakt. (trX, trY : de 'leerwaarden' en teX, teY: de 'testwaarden') .
Na het definieren van X en Y (Python maakt verschil tussen hoofd- en kleine letters) wordt een 'weight-matrix' van 784 (28*28) bij 10 gevuld met de kleine, random waarden.  

tbc ...


import theano
from theano import tensor as T
import numpy as np
from load import mnist

def floatX(X):
    return np.asarray(X, dtype=theano.config.floatX)

def init_weights(shape):
    return theano.shared(floatX(np.random.randn(*shape) * 0.01))

def model(X, w):
    return T.nnet.softmax(T.dot(X, w))

trX, teX, trY, teY = mnist(onehot=True)

X = T.fmatrix()
Y = T.fmatrix()

w = init_weights((784, 10))

py_x = model(X, w)
y_pred = T.argmax(py_x, axis=1)

cost = T.mean(T.nnet.categorical_crossentropy(py_x, Y))
gradient = T.grad(cost=cost, wrt=w)
update = [[w, w - gradient * 0.05]]

train = theano.function(inputs=[X, Y], outputs=cost, updates=update, allow_input_downcast=True)
predict = theano.function(inputs=[X], outputs=y_pred, allow_input_downcast=True)

for i in range(100):
    for start, end in zip(range(0, len(trX), 128), range(128, len(trX), 128)):
        cost = train(trX[start:end], trY[start:end])
    print i, np.mean(np.argmax(teY, axis=1) == predict(teX))

# Visualize the values of 'w' in2_logistic_regression.py
import matplotlib.pyplot as plt
from mpl_toolkits.axes_grid1 import ImageGrid

def fillim(c):
    im = w[0:784,c].eval()*50
    im.shape = 28,28
    return im

fig = plt.figure(1, (5., 5.))
grid = ImageGrid(fig, 111, # similar to subplot(111)
                 nrows_ncols = (2, 5), # creates 2x2 grid of axes
                 axes_pad=0.1, # pad between axes in inch.
                 )

for c in range(10):
    grid[c].imshow(fillim(c),cmap=plt.cm.gray)


plt.show()

Per leercyclus groeit de betrouwbaarheid langzaam op naar 92,5 %:

0 0.8861
1 0.8986
2 0.9048
3 0.9078
4 0.9098
5 0.9115
6 0.9127
7 0.9145
8 0.9154
9 0.916
10 0.9168
11 0.9164
....
94 0.9248
95 0.9248
96 0.9248
97 0.9249
98 0.9249
99 0.9249

Geen opmerkingen:

Een reactie posten