
- 다양한 워크플로
 
Sequential 모델 , Dense층에 익숙해졌고 훈련,평가, 추론을 위해
내장된 compile(),fit(),evaluate(),predict() api를 사용해보았다.

가장 시작하기 쉬운 api 이다 . 기본적으로 하나의 파이썬 리스트이다.
따라서 단순히 층을 쌓을 수 만, 있다.
Sequential모델은 사용하기 쉽지만 적용할 수 있는 곳이 극히 제한된다.
하나의 입력과 하나의 출력을 가지며 순서대로 층을 쌓은 모델만 표현할 수 있다.
from tensorflow import keras
from tensorflow.keras import layers
model = keras.Sequential([
	layers.Dense(64,activation= "relu"),
    layers.Dense(10, activation = "softmax")
    
   ])
   
model = keras.Sequential()
model.add(layers.Dense(64,activation = "relu")
model.add(layers.Dense(10,activation= "softmax")
   
층의 가중치 크기가 입력 크기에 따라 달라진다.
즉 , 입력 크기를 알기 전까지 가중치를 만들 수 없다.
예)

예2)

model.build(input_shape=(None,3))
여기서 ,
None은 sample갯수
3은 특성의 갯수이다
build() 메서드가 호출된 후 디버깅에 유용한 summary()메서드를 사용하여 모델 구조를 출력할 수 있다.
model.summary()

model = keras.Sequential()
model.add(keras.Input(shape=(3,)))
model.add(layers.Dense(64,activation="relu")
Sequential모델은 사용하기 쉽지만 적용할 수 있는 곳이 극히 제한된다.
하나의 입력과 하나의 출력을 가지며 순서대로 층을 쌓은 모델만 표현할 수 있다.
실제론, 다중입력과 다중 출력 또는 비선형적인 구조를 가진 모델을 자주 만날 수 있다.
예제 코드 층 2개)
inputs = Keras.Input(shape=(3,), name="my_input")
features = layers.Dense(64,activation="relu")(inputs)
outputs = layers.Dense(10,activation='softmax")(features)
model= keras.Model(inputs=inputs, outputs=outputs)
inputs.shape
-> (None,3)
inputs.dtype
-> float32
위 같은 객체를 심볼릭 텐서라고 부른다. 실제 데이터를 가지고 있지는 않지만 , 사용할 떄 모델이 보게 될 데이터 텐서의 사양이 인코딩되어 있다. 즉 , 미래의 데이터 텐서를 나타낸다.
vocabulary_size = 10000    # layer를 3개를 만듬
num_tags = 100
num_departments = 4
title = keras.Input(shape=(vocabulary_size,), name="title")
text_body = keras.Input(shape=(vocabulary_size,), name="text_body")
tags = keras.Input(shape=(num_tags,), name="tags")
features = layers.Concatenate()([title, text_body, tags])
features = layers.Dense(64, activation="relu")(features)
priority = layers.Dense(1, activation="sigmoid", name="priority")(features)
department = layers.Dense(
    num_departments, activation="softmax", name="department")(features)
model = keras.Model(inputs=[title, text_body, tags], outputs=[priority, department])
-> call함수를 부르는 것 .
-> init 함수를 부르는 것
-> 묶어서 주면 된다.
import numpy as np  
num_samples = 1280
title_data = np.random.randint(0, 2, size=(num_samples, vocabulary_size))
text_body_data = np.random.randint(0, 2, size=(num_samples, vocabulary_size))
tags_data = np.random.randint(0, 2, size=(num_samples, num_tags))
priority_data = np.random.random(size=(num_samples, 1))  
department_data = np.random.randint(0, 2, size=(num_samples, num_departments))
model.compile(optimizer="rmsprop",
              loss=["mean_squared_error", "categorical_crossentropy"],
              metrics=[["mean_absolute_error"], ["accuracy"]])  
model.fit([title_data, text_body_data, tags_data],  
          [priority_data, department_data],   
          epochs=1)
model.evaluate([title_data, text_body_data, tags_data],  
               [priority_data, department_data])
priority_preds, department_preds = model.predict([title_data, text_body_data, tags_data])  
1.priority_data = np.random/random(size=(num_samples,1))
2.department_data = np.random.random(0,2,size = (num_samples,num_departments))
loss = ["mean_squared_error" ,"categorical_crossentropy"].
metrics = [["mean_absolute_error"],["accuracy"]])  -> 꺽새를 써줘야한다
위 코드 인덱스 순서대로 각각 1,2에 적용된다.
 loss={"priority": "mean_squared_error", "department": "categorical_crossentropy"},
              metrics={"priority": ["mean_absolute_error"], "department": ["accuracy"]})
              
              
이렇게 받을 수 도 있습니다.

이 그림 설명을 하자면,
input shape = 3개
input_layer = 1개
hidden_layer = 1개
output_layer = 1개
output shape = 2개
show_shapes 가 그런 기능을 한다.
간단한 서브클래싱 모델
class CustomerTicketModel(keras.Model):  #call이란 메소드 , predict할떄 불린다. ,init이랑 call을 override한것
    def __init__(self, num_departments):
        super().__init__()                            #super() 중요하다.
        self.concat_layer = layers.Concatenate()
        self.mixing_layer = layers.Dense(64, activation="relu")
        self.priority_scorer = layers.Dense(1, activation="sigmoid")
        self.department_classifier = layers.Dense(
            num_departments, activation="softmax")
    def call(self, inputs):
        title = inputs["title"]   #input안에 들어있는 것 , 딕셔너리로 와야된다.
        text_body = inputs["text_body"]
        tags = inputs["tags"]
        features = self.concat_layer([title, text_body, tags])
        features = self.mixing_layer(features)
        priority = self.priority_scorer(features)
        department = self.department_classifier(features)
        return priority, department
<클래스의 객체를 만들고 , 호출할떄 가중치를 만든다)
model = CustomerTicketModel(num_departments=4)
priority, department = model({"title" :title_data , "text_body" :text_body_data, "tags" : tags_data})