XOR을 신경망으로 분류해보자


XOR 데이터


Logistic Regression 모델

import numpy as np
import tensorflow as tf

x_data = np.array([[0, 0],
                   [0, 1],
                   [1, 0],
                   [1, 1]], dtype=np.float32)

y_data = np.array([[0],
                   [1],
                   [1], [0]], dtype=np.float32)

X = tf.placeholder(tf.float32)
Y = tf.placeholder(tf.float32)
W = tf.Variable(tf.random_normal([2, 1]), name='weight')
b = tf.Variable(tf.random_normal([1]), name='bias')

hypothesis = tf.sigmoid(tf.matmul(X, W) + b)

cost = -tf.reduce_mean(Y * tf.log(hypothesis) + (1 - Y) * tf.log(1 - hypothesis))
train = tf.train.GradientDescentOptimizer(learning_rate=0.1).minimize(cost)

# 모델의 정확도 계산
# hypothesis > 0 이면 참, 아니면 거짓)
predicted = tf.cast(hypothesis > 0.5, dtype=tf.float32)
accuracy = tf.reduce_mean(tf.cast(tf.equal(predicted, Y), dtype=tf.float32))

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())

    for step in range(10001):
        sess.run(train, feed_dict={X: x_data, Y: y_data})
        if step % 1000 == 0:
            print(f'step = {step:06}, cost : {sess.run(cost, feed_dict={X: x_data, Y: y_data})}, '
                  f'weight : {tf.squeeze(sess.run(W)).eval(session=sess)}')

    h, c, a = sess.run([hypothesis, predicted, accuracy], feed_dict={X: x_data, Y: y_data})
    print(f'Hypothesis : {tf.squeeze(h).eval(session=sess)}')
    print(f'Correct : {tf.squeeze(c).eval(session=sess)}')
    print(f'Accuracy : {a*100:.6}%')
step = 000000, cost : 0.8311277627944946, weight : [-0.59255368  2.05449486]
step = 001000, cost : 0.6931628584861755, weight : [ 0.01237938  0.01779066]
step = 002000, cost : 0.6931471824645996, weight : [ 0.00029095  0.0003012 ]
step = 003000, cost : 0.6931471824645996, weight : [  5.78627623e-06   5.79754351e-06]
step = 004000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 005000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 006000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 007000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 008000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 009000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
step = 010000, cost : 0.6931471824645996, weight : [  1.32766417e-07   1.32112120e-07]
Hypothesis : [ 0.5  0.5  0.5  0.5]
Correct : [ 0.  0.  0.  0.]
Accuracy : 50.0%


Neural Network 모델

import numpy as np
import tensorflow as tf

x_data = np.array([[0, 0],
                   [0, 1],
                   [1, 0],
                   [1, 1]], dtype=np.float32)

y_data = np.array([[0],
                   [1],
                   [1], [0]], dtype=np.float32)

X = tf.placeholder(tf.float32)
Y = tf.placeholder(tf.float32)

# Neural Network 적용
W1 = tf.Variable(tf.random_normal([2, 1]), name='weight1')
b1 = tf.Variable(tf.random_normal([2]), name='bias1')
layer1 = tf.sigmoid(tf.matmul(X, W1) + b1)

W2 = tf.Variable(tf.random_normal([2, 1]), name='weight2')
b2 = tf.Variable(tf.random_normal([1]), name='bias2')
hypothesis = tf.sigmoid(tf.matmul(layer1, W2) + b2)

cost = -tf.reduce_mean(Y * tf.log(hypothesis) + (1 - Y) * tf.log(1 - hypothesis))
train = tf.train.GradientDescentOptimizer(learning_rate=0.1).minimize(cost)

# 모델의 정확도 계산
# hypothesis > 0 이면 참, 아니면 거짓)
predicted = tf.cast(hypothesis > 0.5, dtype=tf.float32)
accuracy = tf.reduce_mean(tf.cast(tf.equal(predicted, Y), dtype=tf.float32))

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())

    for step in range(10001):
        sess.run(train, feed_dict={X: x_data, Y: y_data})
        if step % 1000 == 0:
            print(f'step = {step:06}, cost : {sess.run(cost, feed_dict={X: x_data, Y: y_data}):.10}, '
                  f'weight : {tf.squeeze(sess.run(W1)).eval(session=sess)}, '
                  f'{tf.squeeze(sess.run(W2)).eval(session=sess)}')

    h, c, a = sess.run([hypothesis, predicted, accuracy], feed_dict={X: x_data, Y: y_data})
    print(f'Hypothesis : {tf.squeeze(h).eval(session=sess)}')
    print(f'Correct : {tf.squeeze(c).eval(session=sess)}')
    print(f'Accuracy : {a*100:.6}%')
step = 000000, cost : 0.6963943839, weight : [ 0.37977377 -0.03527401], [-0.2952694  -0.10899331]
step = 001000, cost : 0.6927730441, weight : [ 0.42299902 -0.20793314], [-0.39537558 -0.13621624]
step = 002000, cost : 0.6917776465, weight : [ 0.57296711 -0.44276038], [-0.50253206 -0.09007944]
step = 003000, cost : 0.6853944063, weight : [ 0.98696107 -0.93629724], [-0.83750314  0.06653196]
step = 004000, cost : 0.4990587234, weight : [ 2.54613757 -2.89969301], [-2.36907244  1.84388542]
step = 005000, cost : 0.1204189509, weight : [ 4.94409466 -5.14697409], [-5.11362267  5.43273211]
step = 006000, cost : 0.05705790967, weight : [ 5.75085926 -5.89725971], [-6.50368214  6.9214716 ]
step = 007000, cost : 0.03641526401, weight : [ 6.16756582 -6.2878871 ], [-7.34480333  7.78554535]
step = 008000, cost : 0.02652502432, weight : [ 6.43835545 -6.54318571], [-7.94078159  8.3894968 ]
step = 009000, cost : 0.02078646049, weight : [ 6.63547897 -6.72984171], [-8.4005928   8.85260773]
step = 010000, cost : 0.01705784164, weight : [ 6.78890705 -6.87561798], [-8.77430153  9.2277565 ]
Hypothesis : [ 0.01516829  0.97779286  0.98493963  0.01519784]
Correct : [ 0.  1.  1.  0.]
Accuracy : 100.0%


Neural Network에서 neural(=weight)를 늘리려면?



  • weight 변수를 지정할 때, shape의 모양을 변경하면 된다
    • 가설식의 계산값이 더 정확해진다!
W1 = tf.Variable(tf.random_normal([2, 10]), name='weight1')
b1 = tf.Variable(tf.random_normal([10]), name='bias1')
layer1 = tf.sigmoid(tf.matmul(X, W1) + b1)

W2 = tf.Variable(tf.random_normal([10, 1]), name='weight2')
b2 = tf.Variable(tf.random_normal([1]), name='bias2')
hypothesis = tf.sigmoid(tf.matmul(layer1, W2) + b2)
Hypothesis : [ 0.00381555  0.99342114  0.99458128  0.00839256]
Correct : [ 0.  1.  1.  0.]
Accuracy : 100.0%


Deep Neural Network

  • 신경망의 층을 더 깊게 만들기 위해서는 layer를 늘려주면 된다
  • 신경망을 4개로 만들어 보면, 모델이 더욱 최적화되는 것을 알 수 있다
W1 = tf.Variable(tf.random_normal([2, 10]), name='weight1')
b1 = tf.Variable(tf.random_normal([10]), name='bias1')
layer1 = tf.sigmoid(tf.matmul(X, W1) + b1)

W2 = tf.Variable(tf.random_normal([10, 10]), name='weight2')
b2 = tf.Variable(tf.random_normal([10]), name='bias2')
layer2 = tf.sigmoid(tf.matmul(layer1, W2) + b2)

W3 = tf.Variable(tf.random_normal([10, 10]), name='weight2')
b3 = tf.Variable(tf.random_normal([10]), name='bias2')
layer3 = tf.sigmoid(tf.matmul(layer2, W3) + b3)

W4 = tf.Variable(tf.random_normal([10, 1]), name='weight2')
b4 = tf.Variable(tf.random_normal([1]), name='bias2')
hypothesis = tf.sigmoid(tf.matmul(layer3, W4) + b4)
Hypothesis : [ 0.0014578   0.99773043  0.99896216  0.00163728]
Correct : [ 0.  1.  1.  0.]
Accuracy : 100.0%


+ Recent posts