안녕하세요. 문범우입니다.
이번 포스팅에서는 우리가 Deep Neural Network 에 대해 이론으로 배웠던 내용들을 실제로 텐서플로우로 구현해보도록 하겠습니다.
우리가 아래 포스팅에서 softmax classifier를 이용하여 mnist 데이터를 예측해보는 모델을 만들어봤었는데, 이때 정확도가 약 83%도 나왔습니다. 이를 DNN으로 구현해보면서 정확도를 최대 98%까지 끌어올려보도록 하겠습니다.
텐서플로우(Tensor Flow) #10_ MNIST DATA
* 해당 포스트의 모든 내용은 김성훈 교수님의 '모두를 위한 딥러닝'을 바탕으로 제작되었습니다.
관련한 상세 내용은 아래 링크를 참고해주세요.
1. MNIST Data 다루기
우리가 MNIST Data에 대해서는 위에서 언급했던 아래 포스팅에서 다루어 보았습니다.
보다 자세한 내용은 해당 글을 참고하시면 되겠습니다.
텐서플로우(Tensor Flow) #10_ MNIST DATA
이때 작성했던 코드를 기본으로 이번 포스팅을 시작할 것이며 그 코드는 아래와 같습니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 | import tensorflow as tf import numpy as np import matplotlib.pyplot as plt import random from tensorflow.examples.tutorials.mnist import input_data # read data mnist = input_data.read_data_sets("/~/deep_learning_zeroToAll/", one_hot=True) nb_classes = 10 X = tf.placeholder(tf.float32,[None,784]) Y = tf.placeholder(tf.float32,[None,nb_classes]) W = tf.Variable(tf.random_normal([784,nb_classes])) b = tf.Variable(tf.random_normal([nb_classes])) hypothesis = tf.nn.softmax(tf.matmul(X, W) + b) cost = tf.reduce_mean(-tf.reduce_sum(Y * tf.log(hypothesis), axis = 1)) optimizer = tf.train.GradientDescentOptimizer(learning_rate = 0.1).minimize(cost) is_correct = tf.equal(tf.arg_max(hypothesis,1), tf.arg_max(Y, 1)) accuracy = tf.reduce_mean(tf.cast(is_correct,tf.float32)) training_epochs = 15 batch_size = 100 with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for epoch in range(training_epochs): avg_cost = 0 total_batch = int(mnist.train.num_examples / batch_size) for i in range(total_batch): batch_xs, batch_ys = mnist.train.next_batch(batch_size) c, _= sess.run([cost,optimizer], feed_dict={X: batch_xs, Y: batch_ys}) avg_cost += c / total_batch print('Epoch:', '%04d' % (epoch + 1), 'cost = ', '{:.9f}'.format(avg_cost)) print("Learning finished") print("Accuracy: ", accuracy.eval(session=sess, feed_dict={X: mnist.test.images, Y: mnist.test.labels})) # Get one and predict using matplotlib r = random.randint(0, mnist.test.num_examples - 1) print("Label: ", sess.run(tf.argmax(mnist.test.labels[r:r + 1], 1))) print("Prediction: ", sess.run( tf.argmax(hypothesis, 1), feed_dict={X: mnist.test.images[r:r + 1]})) plt.imshow( mnist.test.images[r:r + 1].reshape(28, 28), cmap='Greys', interpolation='nearest') plt.show() | cs |
( mnist dataset 경로를 알맞게 설정하세요. )
해당코드로 코드를 돌려보면 아래와 같은 결과가 나옵니다.
위의 결과 처럼, 약 84%의 결과를 보이고 있습니다.
이제 하나씩 우리가 배웠던 내용을 추가해보면서 정확도를 올려보도록 하겠습니다.
2. Deep, Wide and ReLU
딥러닝(DeepLearning) #4_ ReLU::Rectified Linear Unit먼저 우리가 적용해볼 것은 모델을 보다 deep하고, wide하게 layer를 만들면서 sigmoid 함수 대신에 ReLU 함수를 적용시키는 것 입니다.
또한 optimizer 함수를 AdamOptimizer 함수로 바꾸었는데, 이에 대해서는 크게 생각하지 않고, 더 좋은 것이기 때문에 사용한다는 점만 알아두도록 하겠습니다.
따라서 코드를 아래와 같이 수정하였습니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 | import tensorflow as tf import matplotlib.pyplot as plt import random from tensorflow.examples.tutorials.mnist import input_data tf.set_random_seed(777) # read data mnist = input_data.read_data_sets("/~/deep_learning_zeroToAll/", one_hot=True) nb_classes = 10 X = tf.placeholder(tf.float32,[None,784]) Y = tf.placeholder(tf.float32,[None,nb_classes]) # W = tf.Variable(tf.random_normal([784,nb_classes])) # b = tf.Variable(tf.random_normal([nb_classes])) W1 = tf.Variable(tf.random_normal([784,256])) b1 = tf.Variable(tf.random_normal([256])) L1 = tf.nn.relu(tf.matmul(X, W1) + b1) W2 = tf.Variable(tf.random_normal([256,256])) b2 = tf.Variable(tf.random_normal([256])) L2 = tf.nn.relu(tf.matmul(L1, W2) + b2) W3 = tf.Variable(tf.random_normal([256,10])) b3 = tf.Variable(tf.random_normal([10])) hypothesis = tf.matmul(L2, W3) + b3 cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits = hypothesis, labels=Y)) optimizer = tf.train.AdamOptimizer(learning_rate = 0.001).minimize(cost) is_correct = tf.equal(tf.arg_max(hypothesis,1), tf.arg_max(Y, 1)) accuracy = tf.reduce_mean(tf.cast(is_correct,tf.float32)) training_epochs = 15 batch_size = 100 with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for epoch in range(training_epochs): avg_cost = 0 total_batch = int(mnist.train.num_examples / batch_size) for i in range(total_batch): batch_xs, batch_ys = mnist.train.next_batch(batch_size) c, _= sess.run([cost,optimizer], feed_dict={X: batch_xs, Y: batch_ys}) avg_cost += c / total_batch print('Epoch:', '%04d' % (epoch + 1), 'cost = ', '{:.9f}'.format(avg_cost)) print("Learning finished") print("Accuracy: ", accuracy.eval(session=sess, feed_dict={X: mnist.test.images, Y: mnist.test.labels})) # Get one and predict using matplotlib r = random.randint(0, mnist.test.num_examples - 1) print("Label: ", sess.run(tf.argmax(mnist.test.labels[r:r + 1], 1))) print("Prediction: ", sess.run( tf.argmax(hypothesis, 1), feed_dict={X: mnist.test.images[r:r + 1]})) plt.imshow( mnist.test.images[r:r + 1].reshape(28, 28), cmap='Greys', interpolation='nearest') plt.show() | cs |
이렇게, 3개의 ReLU함수를 적용한 layer로 학습을 진행하니 아래 결과와 같이 약 94%의 정확도를 가지게 되었습니다.
3. Xavier initialize
딥러닝(DeepLearning) #5_ Restricted Belief Machine & Xavier initialize
이번에는 초기값을 건드려 보겠습니다.
Xavier initialize를 이용하여 아래와 같이 코드를 수정하였습니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 | import tensorflow as tf import matplotlib.pyplot as plt import random from tensorflow.examples.tutorials.mnist import input_data tf.set_random_seed(777) # read data mnist = input_data.read_data_sets("/~/deep_learning_zeroToAll/", one_hot=True) nb_classes = 10 X = tf.placeholder(tf.float32,[None,784]) Y = tf.placeholder(tf.float32,[None,nb_classes]) # W = tf.Variable(tf.random_normal([784,nb_classes])) # b = tf.Variable(tf.random_normal([nb_classes])) W1 = tf.get_variable("W1",shape=[784,256], initializer=tf.contrib.layers.xavier_initializer()) b1 = tf.Variable(tf.random_normal([256])) L1 = tf.nn.relu(tf.matmul(X, W1) + b1) W2 = tf.get_variable("W2",shape=[256,256], initializer=tf.contrib.layers.xavier_initializer()) b2 = tf.Variable(tf.random_normal([256])) L2 = tf.nn.relu(tf.matmul(L1, W2) + b2) W3 = tf.get_variable("W3",shape=[256,10], initializer=tf.contrib.layers.xavier_initializer()) b3 = tf.Variable(tf.random_normal([10])) hypothesis = tf.matmul(L2, W3) + b3 cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits = hypothesis, labels=Y)) optimizer = tf.train.AdamOptimizer(learning_rate = 0.001).minimize(cost) is_correct = tf.equal(tf.arg_max(hypothesis,1), tf.arg_max(Y, 1)) accuracy = tf.reduce_mean(tf.cast(is_correct,tf.float32)) training_epochs = 15 batch_size = 100 with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for epoch in range(training_epochs): avg_cost = 0 total_batch = int(mnist.train.num_examples / batch_size) for i in range(total_batch): batch_xs, batch_ys = mnist.train.next_batch(batch_size) c, _= sess.run([cost,optimizer], feed_dict={X: batch_xs, Y: batch_ys}) avg_cost += c / total_batch print('Epoch:', '%04d' % (epoch + 1), 'cost = ', '{:.9f}'.format(avg_cost)) print("Learning finished") print("Accuracy: ", accuracy.eval(session=sess, feed_dict={X: mnist.test.images, Y: mnist.test.labels})) # Get one and predict using matplotlib r = random.randint(0, mnist.test.num_examples - 1) print("Label: ", sess.run(tf.argmax(mnist.test.labels[r:r + 1], 1))) print("Prediction: ", sess.run( tf.argmax(hypothesis, 1), feed_dict={X: mnist.test.images[r:r + 1]})) plt.imshow( mnist.test.images[r:r + 1].reshape(28, 28), cmap='Greys', interpolation='nearest') plt.show() | cs |
각 레이어의 초기값을 랜덤하게 지정하지 않고, xavier initialize를 이용하여 결과를 확인해보니 아래와 같습니다.
위와 같이 약 97%의 정확도를 보여주고 있습니다.
4. Drop out
딥러닝(DeepLearning) #6_ Dropout and Ensemble그럼 이번에는 우리의 모델을 더 깊고, 더 넓게 만들어 보겠습니다.
현재까지는 3개의 layer를 가진 모델이었는데 아래코드와 같이, 5단으로 넓히면서 더 wide하게 모델을 만들어봅니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 | import tensorflow as tf import matplotlib.pyplot as plt import random from tensorflow.examples.tutorials.mnist import input_data tf.set_random_seed(777) # read data mnist = input_data.read_data_sets("/~/deep_learning_zeroToAll/", one_hot=True) nb_classes = 10 X = tf.placeholder(tf.float32,[None,784]) Y = tf.placeholder(tf.float32,[None,nb_classes]) # W = tf.Variable(tf.random_normal([784,nb_classes])) # b = tf.Variable(tf.random_normal([nb_classes])) W1 = tf.get_variable("W1",shape=[784,512], initializer=tf.contrib.layers.xavier_initializer()) b1 = tf.Variable(tf.random_normal([512])) L1 = tf.nn.relu(tf.matmul(X, W1) + b1) W2 = tf.get_variable("W2",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b2 = tf.Variable(tf.random_normal([512])) L2 = tf.nn.relu(tf.matmul(L1, W2) + b2) W3 = tf.get_variable("W3",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b3 = tf.Variable(tf.random_normal([512])) L3 = tf.nn.relu(tf.matmul(L2, W3) + b3) W4 = tf.get_variable("W4",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b4 = tf.Variable(tf.random_normal([512])) L4 = tf.nn.relu(tf.matmul(L3, W4) + b4) W5 = tf.get_variable("W5",shape=[512,10], initializer=tf.contrib.layers.xavier_initializer()) b5 = tf.Variable(tf.random_normal([10])) hypothesis = tf.matmul(L4, W5) + b5 cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits = hypothesis, labels=Y)) optimizer = tf.train.AdamOptimizer(learning_rate = 0.001).minimize(cost) is_correct = tf.equal(tf.arg_max(hypothesis,1), tf.arg_max(Y, 1)) accuracy = tf.reduce_mean(tf.cast(is_correct,tf.float32)) training_epochs = 15 batch_size = 100 with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for epoch in range(training_epochs): avg_cost = 0 total_batch = int(mnist.train.num_examples / batch_size) for i in range(total_batch): batch_xs, batch_ys = mnist.train.next_batch(batch_size) c, _= sess.run([cost,optimizer], feed_dict={X: batch_xs, Y: batch_ys}) avg_cost += c / total_batch print('Epoch:', '%04d' % (epoch + 1), 'cost = ', '{:.9f}'.format(avg_cost)) print("Learning finished") print("Accuracy: ", accuracy.eval(session=sess, feed_dict={X: mnist.test.images, Y: mnist.test.labels})) # Get one and predict using matplotlib r = random.randint(0, mnist.test.num_examples - 1) print("Label: ", sess.run(tf.argmax(mnist.test.labels[r:r + 1], 1))) print("Prediction: ", sess.run( tf.argmax(hypothesis, 1), feed_dict={X: mnist.test.images[r:r + 1]})) plt.imshow( mnist.test.images[r:r + 1].reshape(28, 28), cmap='Greys', interpolation='nearest') plt.show() | cs |
위와 같이, 다른 것들은 모두 그대로 두고 layer를 5개로 확장하면서 보다 wide 하게 만들었습니다.
결과는 어떨까요?
미세하지만, 오히려 이전보다 정확도가 떨어졌습니다.
보다 더 깊고, 넓게 모델을 만들었는데, 왜그럴까요?
바로 우리가 배웠던 overfitting 때문입니다.
이를 해결하기 위해서 우리는 dropout 이라는 것을 배웠고, 바로 코드에 적용시켜보도록 하겠습니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 | import tensorflow as tf import matplotlib.pyplot as plt import random from tensorflow.examples.tutorials.mnist import input_data tf.set_random_seed(777) # read data mnist = input_data.read_data_sets("/~/deep_learning_zeroToAll/", one_hot=True) nb_classes = 10 keep_prob = tf.placeholder(tf.float32) X = tf.placeholder(tf.float32,[None,784]) Y = tf.placeholder(tf.float32,[None,nb_classes]) # W = tf.Variable(tf.random_normal([784,nb_classes])) # b = tf.Variable(tf.random_normal([nb_classes])) W1 = tf.get_variable("W1",shape=[784,512], initializer=tf.contrib.layers.xavier_initializer()) b1 = tf.Variable(tf.random_normal([512])) L1 = tf.nn.relu(tf.matmul(X, W1) + b1) L1 = tf.nn.dropout(L1, keep_prob=keep_prob) W2 = tf.get_variable("W2",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b2 = tf.Variable(tf.random_normal([512])) L2 = tf.nn.relu(tf.matmul(L1, W2) + b2) L2 = tf.nn.dropout(L2, keep_prob=keep_prob) W3 = tf.get_variable("W3",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b3 = tf.Variable(tf.random_normal([512])) L3 = tf.nn.relu(tf.matmul(L2, W3) + b3) L3 = tf.nn.dropout(L3, keep_prob=keep_prob) W4 = tf.get_variable("W4",shape=[512,512], initializer=tf.contrib.layers.xavier_initializer()) b4 = tf.Variable(tf.random_normal([512])) L4 = tf.nn.relu(tf.matmul(L3, W4) + b4) L4 = tf.nn.dropout(L4, keep_prob=keep_prob) W5 = tf.get_variable("W5",shape=[512,10], initializer=tf.contrib.layers.xavier_initializer()) b5 = tf.Variable(tf.random_normal([10])) hypothesis = tf.matmul(L4, W5) + b5 cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits = hypothesis, labels=Y)) optimizer = tf.train.AdamOptimizer(learning_rate = 0.001).minimize(cost) is_correct = tf.equal(tf.arg_max(hypothesis,1), tf.arg_max(Y, 1)) accuracy = tf.reduce_mean(tf.cast(is_correct,tf.float32)) training_epochs = 15 batch_size = 100 with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for epoch in range(training_epochs): avg_cost = 0 total_batch = int(mnist.train.num_examples / batch_size) for i in range(total_batch): batch_xs, batch_ys = mnist.train.next_batch(batch_size) c, _= sess.run([cost,optimizer], feed_dict={X: batch_xs, Y: batch_ys, keep_prob: 0.7}) avg_cost += c / total_batch print('Epoch:', '%04d' % (epoch + 1), 'cost = ', '{:.9f}'.format(avg_cost)) print("Learning finished") print("Accuracy: ", accuracy.eval(session=sess, feed_dict={X: mnist.test.images, Y: mnist.test.labels, keep_prob: 1})) # Get one and predict using matplotlib r = random.randint(0, mnist.test.num_examples - 1) print("Label: ", sess.run(tf.argmax(mnist.test.labels[r:r + 1], 1))) print("Prediction: ", sess.run( tf.argmax(hypothesis, 1), feed_dict={X: mnist.test.images[r:r + 1], keep_prob: 1})) plt.imshow( mnist.test.images[r:r + 1].reshape(28, 28), cmap='Greys', interpolation='nearest') plt.show() | cs |
위와 같이 keep_prob 라는 변수를 새로 만들어서, 각 레이어마다 dropout 함수를 적용시키고 이때 keep_prob 값을 변수값으로 넣었습니다.
이후 훈련할때 keep_prob 값을 feed_dict에서 0.7로 주었으며 실제로 예측할때는 1값을 주었습니다.
이를 통해 나오는 결과는 아래와 같습니다.
위의 결과를 확인하면 정확도가 98%를 넘기는 것을 확인할 수 있습니다.
이렇게 우리가 그동안 배웠던 개념들을 실제로 텐서플로우에서 구현해보고, 그것들이 얼마나 정확도를 높여주는지 확인해보았습니다.
'AI & BigData > 모두를 위한 딥러닝(정리)' 카테고리의 다른 글
딥러닝(DeepLearning) #8_pooling and others (0) | 2018.05.04 |
---|---|
딥러닝(DeepLearning) #7_CNN(Convolutional Neural Networks) introduction (0) | 2018.05.03 |
딥러닝(DeepLearning) #6_ Dropout and Ensemble (0) | 2018.04.20 |
딥러닝(DeepLearning) #5_ Restricted Belief Machine & Xavier initialize (0) | 2018.04.20 |
딥러닝(DeepLearning) #4_ ReLU::Rectified Linear Unit (0) | 2018.04.19 |