tf.Data를 활용하여 csv 파일부터 읽어서 텐서플로우 모델링하기

2019. 6. 16. 18:07분석 Python/Tensorflow

728x90

보통 데이터가 클 경우에 읽는 것도 버거울 경우가 있다. 

아마 내가 여기서 기대하는 것은 읽을 때도 batch 단위로 읽어서 메모리를 다 안 쓰는? 

실제로 그렇게 돌아가는지는 모르겠다.

 

암튼 csv 에서 자체적으로 feature를 쪼개서 학습을 시킬 때 어떻게 해야 하나 고민하다가 방법을 찾아서 공유한다.

 

물론 그리고 바로 모델링도 쉽게 하는 방법까지 해보겠다.

 

아직 해결해야할 점은 Pipeline에서 전처리도 안에서 어떻게 해야 할지다!

여기서 의문인 점은 batch 단위로 전처리를 하게 되는지 그런 것들이 좀 궁금하다. 

큰 데이터에서 어떻게 전처리를 해야 효과적으로 할 수 있는지.... 

 

아무튼 여기선 csv -> 바로 feature와 target으로 나눠서 모델링하는 것으로! 

 

import tensorflow as tf
import re
import numpy as np


CSV_COLUMN_NAMES = ['ID', 'LIMIT_BAL', 'SEX', 'EDUCATION', 'MARRIAGE', 'AGE', 'PAY_0',
       'PAY_2', 'PAY_3', 'PAY_4', 'PAY_5', 'PAY_6', 'BILL_AMT1', 'BILL_AMT2',
       'BILL_AMT3', 'BILL_AMT4', 'BILL_AMT5', 'BILL_AMT6', 'PAY_AMT1',
       'PAY_AMT2', 'PAY_AMT3', 'PAY_AMT4', 'PAY_AMT5', 'PAY_AMT6',
       'default payment next month']
csv_path = "./../../Data/creditcard.csv"

CSV_DEFAULTS = [[0.0]*len(CSV_COLUMN_NAMES)]
CSV_DEFAULTS = np.array(CSV_DEFAULTS).reshape(25,1).tolist()

def parse_row(row):
    fields = tf.decode_csv(records = row, record_defaults = CSV_DEFAULTS)
    features = dict(zip(CSV_COLUMN_NAMES, fields))
    label = features.pop('default payment next month') # remove label from features and store
    return features, label
    
def read_dataset(csv_path):  
    dataset = tf.data.TextLineDataset(filenames = csv_path).skip(count = 1) # skip header
    dataset = dataset.map(map_func = parse_row ) 
    return dataset
    
def train_input_fn(csv_path, batch_size = 128):
    dataset = read_dataset(csv_path)
    dataset = dataset.shuffle(buffer_size = 1000).repeat(count = None).batch(batch_size = batch_size)
    return dataset
    
    
feature_cols = [tf.feature_column.numeric_column(key = k) for k in FEATURE_NAMES]
model = tf.estimator.DNNClassifier(hidden_units=[10,10],
                           feature_columns= feature_cols , 
                                   optimizer=lambda: tf.train.AdamOptimizer(
                                       learning_rate=tf.train.exponential_decay(
                                           learning_rate=0.1,
                                           global_step=tf.train.get_global_step(),
                                           decay_steps=10000, decay_rate=0.96)) )
                                           
model.train(
    input_fn = lambda: train_input_fn(csv_path = csv_path),
    steps = 1000,
)

## 여기 코드는 없다.
metrics = model.evaluate(input_fn = lambda: eval_input_fn(csv_path = "./taxi-valid.csv"))
print("RMSE on dataset = {}".format(metrics["average_loss"]**.5))

 

 

일단 이런 식으로 쉽게 모델링 된다!

하지만 내가 직접 레이어랑 그런 것을 자유롭게 하고 싶을 때 어떻게 해야 할지 고민인데! 

batch_size = 32
dataset= read_dataset(csv_path)
dataset = dataset.batch(batch_size, drop_remainder=True).shuffle(buffer_size = 10*batch_size)

dataset_iterator = dataset.make_one_shot_iterator()
features, labels = dataset_iterator.get_next()
feature.values()

 

이게 근데 Numpy가 아니라 odict 형태로 나오게 된다. 이것도 바로 되는지는 안 해봐서 모르겠다.

 

728x90