[PYTHON] Keras starting from nothing 3rd

Click here for Keras lottery starting from nothing [http://qiita.com/Ishotihadus/items/6ecf5684c2cbaaa6a5ef)

Last review

Last time created a rough data set and trained it roughly.

The input is 5 dimensions and each element is greater than or equal to 0 and less than 1. The output is one-dimensional, -1 if the sum of the input elements is 2.5 or less, 1 if greater than 2.5. Do so-called "two-class classification".

The data set was created as follows. The output is 0 or 1 and then multiplied by 2 to -1 (it becomes -1 or 1).

data = np.random.rand(250,5)
labels = (np.sum(data, axis=1) > 2.5) * 2 - 1

The model was as follows. For the activation function, we used tanh, which has a range of -1 to 1, and for the loss, we used the hinge loss, which is good for the code.

model = Sequential([Dense(20, input_dim=5, activation='tanh'), Dense(1, activation='tanh')])
model.compile('adam', 'hinge', metrics=['accuracy'])

What is a Sequential model?

As mentioned in Part 1, the Sequential model simply puts arrows on each node of the current layer from all the nodes of the previous layer. It is an image that pulls. Sure, it still works as a neural network, but it's a bit uninteresting.

The Functional API solves this problem. You can do something quite complicated, such as putting in the output of two neural networks or sharing layers.

What is Functional API?

Let's create a neural network with the same shape as last time. Since it has the same shape, it seems meaningless to make it, but that is practice.

The Functional API is simply "you can mess up how you connect the arrows." In the Sequential model, it could only be done in the form of A → B → C. But with the Functional API

A  ↘   C → D → E  ↗ B

You will be able to do something like that. I won't do it this time.

Use Functional API

Input layer

First, the input layer.

from keras.layers import Input, Dense
from keras.models import Model

inputs = Input(shape=(5,))

This layer is named Input, but unfortunately there is no documentation.

shape represents the dimension of the input. The notation (5,) feels like something you don't know about Python, but it's just a Tuple (like an array) with only the element 5. It looks like there are multiple elements because of the comma, but there is only one element. It's because it's indistinguishable from just a number without a comma, but I think it's really a shit notation. Python doesn't like this.

Hidden layer

x = Dense(20, activation='tanh')(inputs)

A layer with 20 nodes and ʻinputs` inputs.

Dense means "dense", but I think it's dense in that sense because it pulls all the arrows from all the nodes in the previous layer to all the nodes in this layer.

Output layer

predictions = Dense(1, activation='tanh')(x)

This is almost the same as the hidden layer. No explanation needed.

Functional API Meaning

What does Functional mean?

If you look closely, you can see that Dense is calling that instance as a function. The documentation says that a function call to an instance of a layer will return a tensor.

In the first place, a neural network is roughly a tensor product (or a matrix product in a simpler way). Multiplying the input vector by a matrix, and then multiplying it by a matrix ... is the essence in the first place. Going through a single layer is roughly the same as running a single matrix. The image of multiplying the matrix (tensor) is compared with the function call.

When a function is called, the input tensor is transformed with the specified meaning and output as a tensor again. I think it's easy to understand if you capture it with that kind of image.

I'm not saying anything exactly, so that's it.

By the way, only the ʻInput` layer returns a tensor in the first place (so no function call is needed).

Summary of this program

import numpy as np
from keras.layers import Input, Dense
from keras.models import Model

data = np.random.rand(250,5)
labels = (np.sum(data, axis=1) > 2.5) * 2 - 1

inputs = Input(shape=(5,))
x = Dense(20, activation='tanh')(inputs)
predictions = Dense(1, activation='tanh')(x)

model = Model(input=inputs, output=predictions)
model.compile('adam', 'hinge', metrics=['accuracy'])
model.fit(data, labels, nb_epoch=150, validation_split=0.2)

test = np.random.rand(200, 5)
predict = np.sign(model.predict(test).flatten())
real = (np.sum(test, axis=1) > 2.5) * 2 - 1
print(sum(predict == real) / 200.0)

Except for the writing method, it is exactly the same as Part 2, so I think that the accuracy will be almost the same.

Recommended Posts

Keras starting from nothing 3rd
Keras 5th starting from nothing
Keras starting from nothing 1st
Keras 4th starting from nothing
Keras starting from nothing 2nd
Django starting from scratch (part: 2)
Django starting from scratch (part: 1)
ChIP-seq analysis starting from zero
(Almost) troubleshooting techniques from nothing
[Introduction] From installing kibana to starting
Code wars kata starting from zero