Linear / Poly Regression ทำนาย GDP ประเทศไทย : Machine Learning 101

ปี 2018 อาจะเป็นปีที่ค้าขายไม่ค่อยคึกคักเท่าไหร่ แต่เป็นปีทองของวงการคอมพิวเตอร์เลยก็ว่าได้

หลังจากที่เราเรียน intro ของ Machine Learning มาแล้ว (Intro Machine Learning) และได้ลองเล่น K-NN ที่เป็น Classification (K-NN with Sklearn) จากนั้นก็ทำการวัดประสิทธิภาพของโมเดลของเราแล้ว (Evaluate) เข้าใจคำว่า Over/Under Fitting แล้ว (Over/Under ปัญหาที่มองไม่เห็น) ทีนี้เราก็จะมาลองเล่น Machine Learning ที่เป็น Regression กันในบล็อกนี้

Regression คืออะไร ??

ถ้าใครได้เรียนวิชาสถิติน่าจะเคยได้ยินคำนี้มาก่อนหรือถ้าแปลเป็นไทยนั้นคือ การวิเคราะห์แบบถดทอย นั้นคือการทำนายของตัวแปรชนิดหนึ่งโดนเรียกว่าตัวแปรตาม(Y) โดยอาศัยตัวแปรอื่นๆ เรียกว่าตัวแปรอิสระ(X) โดยเราอาจจะมีตัวแปรอื่นๆได้หลายๆตัวแปร หรือมีแค่ตัวแปรเดียวก็ได้เมื่อทำการทำนายแล้วเราจะได้ output ออกมาเป็น Y ออกมานั้นเอง โดยที่ output จะได้ออกมาเป็นตัวเลข ต่างกับ Classification ที่ได้ออกมาเป็น category / class

Linear/Poly Regression คืออะไร ?

มันคือหลักการของ Regression เหมือนกันแต่ว่าผลลัพธ์ออกมาจะต่างกันโดย Linear ผลลัพธ์จะออกมาเป็นเส้นตรง แต่ Poly จะออกมาเป็นเส้นโค้ง

ตัวอย่าง

มีกราฟ 2 มิติอยู่ 1 อัน จุดสีฟ้าคือ Training Data ของเรา ส่วนเส้นสีแดงคือเส้นที่ใช้ในการทำนาย

ผมอยากจะรู้ว่า ที่ X เป็น 10 จะได้ Y เท่าไหร่ วิธีง่ายๆนั้นคือลากเส้นแกน X ที่ 10 ไปหาเส้นสีแดง แล้วลากจากจุดนั้นไปแกน Y ก็จะได้ค่า Y ออกมานั้นคือ 6.5

สังเกตุในรูปได้ X = 10 ไม่มีข้อมูลอ้างอิง(Training Data)ในแกน Y ก็จริงแต่เราสามารถสร้างเส้นอ้างอิงขึ้นมาได้ และเส้นในรูปก็เป็นเส้นตรง จึงเรียกเส้นนี้ว่า Linear Regression

ใช้หลักการอะไรจึงสร้างเส้นนี้ขึ้นมาได้ ? ถามหมอผี ? ถามหมอดู ?

ถึงตรงนี้ใครไม่ชอบคณิตศาสตร์อาจจะเซงๆหน่อย แต่อยากบอกว่ามันง่ายมากกกกก และปัจจุบันก็มี Lib ที่ช่วยเราสร้างขึ้นมาโดยไม่ต้องเขียนสูตรแล้ว แต่สูตรนี้จะเป็นพื้นฐานนำไปต่อยอดใช้ร่วมกับอย่างอื่นได้อีก (L1/L2,SGD)

คณิตศาสตร์ที่อยู่ใน Linear Regression เราเรียกว่า Normal Equation หน้าที่ของมันคือหาค่า Cost function ที่ต่ำที่สุด (ลากเส้นสีแดงให้สามารถทำนายได้แม่นยำที่สุด)

พอได้สมการ MSE จากนั้นใช้ Matrix Calculation แก้สมการก็จะได้สมการหน้าตาดูง่ายๆออกมาคือ

โดยขั้นแรกนำข้อมูลที่เรามี Training Set เป็นแกน y และมีแกนอ้างอินคือ x ใส่ลงในสมการนี้ (ทั้งหมด) เจ้ามุมในสมการ(theta) ก็จะออกมาเป็นมุมที่เอาไว้ลากเส้นตรงนั้นเอง

วิธีทำนาย

เมื่อได้มุม Theta ออกมาแล้วให้มาทำการ dot matrix กับค่า x ที่เราอยากจะได้นั้นเอง

ก็จะได้ค่า y ออกมาอย่างเช่นในตัวอย่างข้างบน ถ้าเกิดนำ 5 ไป dot matrix กับมุม theta คำตอบที่ได้รับออกมาก็ควรจะเป็น 6.5 นั้นเอง

ลงมือทดลอง

ข้อควรรู้ก่อนปฏิบัติ

  1. Training Data ระหว่างแกน X กับ แกน Y ควรมีความสัมพันธ์ซึ่งกันและกัน เช่น ราคาบ้าน กับ ถิ่นที่ขาย , อุณหภูมิ กับ ความชื้น , GDP กับ จำนวนนักท่องเที่ยว แต่
  2. ระวังข้อมูลแปลกๆใน dataset เช่น GDP มีอยู่ข้อมูลนึงที่มีค่าเป็นพันล้านล้าน หรือ 1 บาท จะทำให้เส้นเราไม่ตรงอย่างที่เราต้องการได้
  3. ขั้นตอนกระบวนการทั้งหมดจะใช้ sklearn ในการทำ จะช่วยลดขั้นตอนยุ่งยากไปได้ (หากใคร Hard core จะเขียนสมการ MSE เองก็ได้ ผลลัพธ์คล้ายกัน)
  4. ในการทดลองนี้จะไม่มีความสัมพันธ์ระหว่าง x และ y ทำให้ค่าอาจไม่ตรงกับความเป็นจริง แต่สามารถดูเป็นแนวทางได้

ขั้นตอนที่หนึ่ง ทำการโหลด Dataset จาก github (คลิกที่นี้) จากนั้นก็เปิด Jupyter Notebook ขึ้นมาแล้ว Code กัน !

ขั้นตอนที่สอง ทำการโค้ดโดยการอ่านไฟล์ csv ด้วย pandas จากนั้นก็แสดงข้อมูลของประเทศไทย

import pandas as pd
data = pd.read_csv(’API_NY.GDP.MKTP.CD_DS2_en_csv_v2_10203569.csv’, sep=’,’, engine=’python’)
y=data[data[’Country Name’] == 'Thailand’].drop([‘Country Name’,’Country Code’,’Indicator Name’,’Indicator Code’])

ทำการเตรียมข้อมูลชุดฝึกทั้งแกน X และ Y

th_T = th.T
y = th_T.values.tolist()
import numpy as np
x=np.arange(1960,1960+58).reshape(-1,1)

จะได้ข้อมูลชุด y ประมาณนี้ และ แกน x ที่เป็นปี

จากนั้นลองดูข้อมูลก่อนว่าลักษณะเป็นอย่างไร

%matplotlib inline 
import matplotlib.pyplot as plt
plt.scatter(x,y)
แกน Y หน่วย พันล้าน

ได้เวลาสร้าง Model สำหรับ Linear Regression แล้วด้วยคำสั่ง

from sklearn.linear_model import LinearRegression
lin_reg = LinearRegression()
lin_reg.fit(x, y)
lin_reg.intercept_, lin_reg.coef_

ก็จะได้มุมกลับมานั้นคือ !

มุม theta นั้นเอง

ทีนี้เราก็สร้างเส้นสีแดงขึ้นมาได้แล้วด้วยคำสั่ง

y_pre = lin_reg.predict(x)
plt.plot(x,y_pre,"r-")
plt.scatter(x,y)
แกน Y หน่วย พันล้าน

ทีนี้ลองคิดเล่นๆดูว่าในปี 2018 ประเทศไทยจะมี GDP เป็นเท่าไหร่

โดยการทำนายของเรา ประเทศไทยในปี 2018 จะมีรายได้ประมาณ 3.3597 พันล้านบาทนั้นเอง เย้ !!!

แต่

ทีนี้ใครที่รู้จัก Regression มาก่อนเมื่อเห็นรูปนี้แล้วจะเข้าใจแล้วว่า Linear Regression ข้อเสียคืออะไร…. นั้นคือ ข้อมูลของเราถ้าต้องการให้มันแม่นยำจริงๆไม่ควรลากเส้นตรง น่าจะเป็นเส้นโค้งน่าจะเวิร์คมากกว่า

แบบนี้น่าจะเวิร์คกว่านะ

แต่วิธีแก้นั้นง่ายมากนั้นคือเปลี่ยนจาก Linear Regression เป็น Poly Regression โดยการเพิ่มข้อมูลของ x เป็นสองเท่าแต่ค่าที่เพิ่มเข้ามาให้ยกกำลังสองจะทำให้ได้เส้นโค้งนั้นเอง ด้วยคำสั่ง Polynomial.fit_transform

from sklearn.preprocessing import PolynomialFeatures
poly_features = PolynomialFeatures(degree=2, include_bias=False)
X=poly_features.fit_transform(x)
lin_reg.fit(X, y)
y_pre = lin_reg.predict(X)
plt.plot(x,y_pre,"r-")
plt.scatter(x,y)

ก็จะได้เส้นโค้งโผล่ออกมานั้นเอง

ทีนี้ลองทำนายปี 2018 อีกสักครั้งหนึ่งแล้วกัน

ทำนายได้ประมาณ 4.5629 พันล้าน แต่ความเป็นจริงน่าจะประมาณ 4.2–4.7 (อ้างอิง) จะเห็นได้ว่า poly ใช้ได้จริงๆ ใกล้เคียงกับที่นักคาดการณ์ได้ทำนายไว้

บทสรุป

การทำนายค่าโดยใช้ Linear / Poly Regression การเลือกใช้นั้นขึ้นอยู่กับสถานการณ์ ว่าข้อมูลของเราเป็นเส้นตรงหรือโค้งแต่ว่าทั้ง 2 ยังมีเรื่องของ Over fitting / Under Fitting อยู่ดีทางแก้ของเราคือใช้ L1/L2 (ประมาณนี้) และในการใช้งานจริงๆเราอาจจะมีแกน X มากกว่า 1 อันซึ่ง Linear/Poly นั้นใช้ Normal Equation หาได้ก็จริง แต่…. จะช้าในการสร้างเส้นขึ้นมา วิธีแก้นั้นก็คือ Gradient Descent

บทความถัดไป

Gradient Descent คีย์เวิร์ดที่ Data Science ต้องรู้จัก !

Github : https://github.com/peeratpop/Machine_Learning_101

Medium : https://medium.com/@pingloaf

facebook : https://www.facebook.com/nping.loaf