선형 모형 :: 텐서플로 기초 - mindscale
Skip to content

선형 모형

딥러닝, 머신 러닝 등에서 가장 기본적은 선형 모형(linear model)입니다. 데이터가 직선 형태를 이루고 있을 것이라고 가정하기 때문에 선형 모형이라고 합니다. 선형 모형을 수식으로 나타내면 다음과 같은 직선의 방정식 형태가 됩니다.

$$ y = wx + b $$

$x$와 $y$는 데이터입니다. $w$는 직선의 기울기입니다. 가중치(weight)나 계수(coefficient)라고도 합니다.

$w$와 $b$는 모형의 형태를 결정하는 값으로 파라미터(parameter)라고 합니다.

$b$는 $x = 0$일 때 $y$의 값으로 $y$ 절편(intercept)이라 하고, 그냥 절편이라고 하거나 또는 편향(bias)이라고도 합니다.

예제 데이터

파이썬 시각화 라이브러리인 seaborn에 내장된 예제 데이터로 선형 모형을 학습시켜보겠습니다.

import seaborn as sns

seaborn 내장 데이터 중에 tips 데이터를 사용합니다.

tips = sns.load_dataset("tips") 
tips.head()
total_bill tip sex smoker day time size
0 16.99 1.01 Female No Sun Dinner 2
1 10.34 1.66 Male No Sun Dinner 3
2 21.01 3.50 Male No Sun Dinner 3
3 23.68 3.31 Male No Sun Dinner 2
4 24.59 3.61 Female No Sun Dinner 4

이 데이터에는 영수증에 찍힌 가격(total_bill)과 고객이 준 팁(tip)이 기록되어 있습니다. 이 두 변수의 관계를 시각화해보면 대체로 선형적인 관계가 있음을 확인할 수 있습니다.

sns.regplot('total_bill', 'tip', tips)
<matplotlib.axes._subplots.AxesSubplot at 0x2038cb751c8>

텐서플로를 이용해 선형 모형 만들기

텐서플로를 이용해서 선형 모형을 만들어보겠습니다.

먼저 텐서플로를 임포트합니다.

import tensorflow as tf

텐서플로에서 keras는 다양한 모형을 쉽게 만들 수 있는 방법을 제공합니다. 먼저 Sequential을 이용해 빈 모형을 만듭니다.

model = tf.keras.models.Sequential()

다음으로 레이어(layer)를 만듭니다. 레이어는 어떤 $x$를 입력 받아, $y$를 출력하는 형태의 계산을 표현합니다. 선형 모형은 $y = wx + b$ 형태의 계산인데, 이런 계산은 Dense 레이어를 사용합니다.

출력하는 $y$도 하나이므로 Dense의 첫 번째 인자는 1이라고 써줍니다.

입력하는 $x$도 하나이므로 input_shape에는 (1, )라고 해줍니다. 그냥 1이라고 하지 않고 (1, )이라고 하는 이유는 나중에 다른 강의에서 자세히 설명할 것입니다. 여기서는 일단 (1, )라고 한다고 알아둡시다.

layer = tf.keras.layers.Dense(1, input_shape=(1,))

모형에 레이어를 추가하면 선형 모형이 완성됩니다.

model.add(layer)

선형 모형 학습시키기

이제 앞서 만들어둔 데이터로 선형 모형을 학습시켜보겠습니다. 여기서 모형을 학습시킨다는 것은 데이터를 통해 $w$와 $b$의 적절한 값을 알아낸다는 것입니다. 현재는 우리가 손으로 만든 데이터이기 때문에 $w$와 $b$가 각각 2, 1이라는 것을 알고 있지만 실제 데이터의 경우에는 학습을 통해 알아내야 합니다.

학습시키기 전에 먼저 모형을 설정해야 합니다. optimizer는 모형을 적합시키는 알고리즘입니다. 여기서는 어떤 알고리즘을 쓰더라도 큰 차이가 없기 때문에 가장 간단한 sgd를 사용하겠습니다.

loss는 학습한 $w$와 $b$를 이용해서 $wx + b$를 계산한 값과 실제 $y$의 오차를 구해서 모형의 정확성을 측정하는 방법입니다. $y$가 연속 변수일 경우에는 mse를 많이 사용한다. mse는 평균오차제곱(Mean Squared Error)이라는 뜻으로 예측 오차의 제곱을 평균 낸 값입니다.

model.compile(optimizer=tf.keras.optimizers.Adam(lr=0.01),
              loss='mse')

이제 학습을 시작하겠습니다. 학습은 임의의 파라미터로 시작합니다. 모형에 데이터를 입력하면 오차를 구할 수 있는데, 이때 오차가 줄어드는 방향으로 파라미터를 수정합니다. 샤워기의 온도를 맞출 때 물이 뜨거우면 왼쪽으로 돌리고, 물이 차가우면 오른쪽으로 돌리는 과정을 반복해서 온도를 맞추는 것과 비슷합니다.

학습에서 한 번의 과정을 epoch라고 합니다. epoch를 늘리면 학습을 더 많이 하므로 파라미터가 좀 더 정확하게 추정될 것입니다. 여기서는 30 epoch를 하겠습니다.

verbose=0verbose=1로 수정하면 진행상황을 실시간으로 확인할 수 있습니다.

x = tips['total_bill'].values
y = tips['tip'].values

result = model.fit(x, y, epochs=30, verbose=0)

학습된 파라미터를 확인합니다. 첫번째 파라미터가 $w$에 해당하는 값이고, 두번째가 $b$에 해당하는 값입니다.

model.weights
[<tf.Variable 'dense_14/kernel:0' shape=(1, 1) dtype=float32, numpy=array([[0.18558289]], dtype=float32)>,
 <tf.Variable 'dense_14/bias:0' shape=(1,) dtype=float32, numpy=array([-0.92574245], dtype=float32)>]

한 epoch다 loss가 얼마나 감소했는지를 확인합니다. 처음에 빠르게 줄어들다가 0에 가까워지면서 점점 기울기가 완만해집니다. 데이터가 완전히 직선 상에 있는 것은 아니므로 loss가 0이 될 수는 없습니다.

plt.plot(result.history['loss'])
[<matplotlib.lines.Line2D at 0x20388e452c8>]