# 구글 드라이브 마운트

# from google.colab import drive
# drive.mount('/gdrive', force_remount=True)
# # /gdrive/My Drive/ (폴더명)
import os
import math
import numpy as np
import tensorflow as tf
import matplotlib.pyplot as plt
from tqdm import tqdm
import cv2
contents = cv2.imread('contents.jpg')
contents = cv2.resize(contents, (224, 224))
# contents=cv2.cvtColor(contents,cv2.COLOR_BGR2RGB)
# contents=contents/255.
plt.imshow(contents)

style = cv2.imread('style.jpg')
style = cv2.resize(style, (224, 224))
# style=cv2.cvtColor(style,cv2.COLOR_BGR2RGB)
# style=style/255.
plt.imshow(style)

vgg_model=tf.keras.applications.VGG16(input_shape=(224,224,3),include_top=False,weights='imagenet')
Downloading data from https://storage.googleapis.com/tensorflow/keras-applications/vgg16/vgg16_weights_tf_dim_ordering_tf_kernels_notop.h5
58892288/58889256 [==============================] - 1s 0us/step
vgg_model.trainable=False
tf.keras.utils.plot_model(vgg_model,show_shapes=True)
style_transfer_model=tf.keras.Model(inputs=[vgg_model.input],outputs=[
                                                            vgg_model.get_layer(name='block1_conv2').output,
                                                            vgg_model.get_layer(name='block2_conv2').output,
                                                            vgg_model.get_layer(name='block3_conv3').output,
                                                            vgg_model.get_layer(name='block4_conv3').output
])
style_transfer_model.summary()
style_true_b1c1,style_true_b2c2,style_true_b3c3,style_true_b4c3=style_transfer_model.predict(np.reshape(style,(-1,224,224,3)))
style_true_b4c3.shape
(1, 28, 28, 512)
plt.imshow(style_true_b1c1[0][:,:,3])

contents_true_b1c1,contents_true_b2c2,contents_true_b3c3,contents_true_b4c3=style_transfer_model.predict(np.reshape(contents,(-1,224,224,3)))
contents_true_b3c3.shape
(1, 56, 56, 256)
plt.imshow(contents_true_b3c3[0][:,:,11])

def gram_matrix(x):
    reshape_x=tf.transpose(x,[2,1,0])
    s = tf.shape(reshape_x)
    reshape_x=tf.reshape(reshape_x,(s[0],s[1]*s[2]))
    reshape_x_t=tf.transpose(reshape_x)
    dot=tf.matmul(reshape_x,reshape_x_t)
    dot=tf.cast(dot,dtype='float32')
    dot=dot/tf.cast(tf.shape(reshape_x)[0], tf.float32)/tf.cast(tf.shape(reshape_x)[1], tf.float32)
    return dot
input_image = cv2.imread('contents.jpg')
input_image = cv2.resize(input_image, (224, 224))
# input_image=cv2.cvtColor(input_image,cv2.COLOR_BGR2RGB)
# input_image=input_image/255.
opt=tf.keras.optimizers.Adam(10.0)
img_avi=np.zeros((224,224,3))
fcc=cv2.VideoWriter_fourcc(*'DIVX')
out=cv2.VideoWriter('style_transfer.avi',fcc,10.0,(224,224))
for epoch in range(50):
    input_image=tf.reshape(input_image,(-1,224,224,3))
    input_image=tf.cast(input_image,dtype='float32')
    input_image = tf.Variable(input_image, dtype=tf.float32)
    with tf.GradientTape() as tape:
        
        b1c1,b2c2,b3c3,b4c3=style_transfer_model(input_image)
        
        s_loss_1=tf.stop_gradient(gram_matrix(style_true_b1c1[0]))-gram_matrix(b1c1[0])
        s_loss_1=tf.reduce_mean(tf.square(s_loss_1))
        s_loss_2=tf.stop_gradient(gram_matrix(style_true_b2c2[0]))-gram_matrix(b2c2[0])
        s_loss_2=tf.reduce_mean(s_loss_2*s_loss_2)
        s_loss_3=tf.stop_gradient(gram_matrix(style_true_b3c3[0]))-gram_matrix(b3c3[0])
        s_loss_3=tf.reduce_mean(s_loss_3*s_loss_3)
        s_loss_4=tf.stop_gradient(gram_matrix(style_true_b4c3[0]))-gram_matrix(b4c3[0])
        s_loss_4=tf.reduce_mean(s_loss_4*s_loss_4)
              
        c_loss_1=contents_true_b1c1-b1c1
        c_loss_1=tf.reduce_mean(tf.square(c_loss_1))
        c_loss_2=contents_true_b2c2-b2c2
        c_loss_2=tf.reduce_mean(tf.square(c_loss_2))
        c_loss_3=contents_true_b3c3-b3c3
        c_loss_3=tf.reduce_mean(tf.square(c_loss_3))
        c_loss_4=contents_true_b4c3-b4c3
        c_loss_4=tf.reduce_mean(tf.square(c_loss_4))

        s_loss=(s_loss_1+s_loss_2+s_loss_3+s_loss_4)
        c_loss=(c_loss_1+c_loss_2+c_loss_3+c_loss_4)/4.
        loss=s_loss*10.0+c_loss_3
    grad=tape.gradient(loss,input_image)
    opt.apply_gradients([(grad,input_image)])
    input_image=tf.cast(input_image,dtype=tf.int32)
    input_image=tf.clip_by_value(input_image,0,255)
    img_avi=input_image.numpy()[0]
    out.write(np.uint8(img_avi))
    print()
    print(epoch+1)
    print('s_loss',s_loss)
    print('c_loss_3',c_loss_3)
plt.imshow(input_image[0][:,:,::-1])
out.release()
cv2.destroyAllWindows()

1
s_loss tf.Tensor(4228450.5, shape=(), dtype=float32)
c_loss_3 tf.Tensor(0.0, shape=(), dtype=float32)

2
s_loss tf.Tensor(2311314.0, shape=(), dtype=float32)
c_loss_3 tf.Tensor(339267.16, shape=(), dtype=float32)

3
s_loss tf.Tensor(1482186.0, shape=(), dtype=float32)
c_loss_3 tf.Tensor(480693.22, shape=(), dtype=float32)

4
s_loss tf.Tensor(793303.1, shape=(), dtype=float32)
c_loss_3 tf.Tensor(512151.34, shape=(), dtype=float32)

5
s_loss tf.Tensor(639529.9, shape=(), dtype=float32)
c_loss_3 tf.Tensor(496290.53, shape=(), dtype=float32)

6
s_loss tf.Tensor(1021584.2, shape=(), dtype=float32)
c_loss_3 tf.Tensor(740942.9, shape=(), dtype=float32)

7
s_loss tf.Tensor(731780.44, shape=(), dtype=float32)
c_loss_3 tf.Tensor(526930.3, shape=(), dtype=float32)

8
s_loss tf.Tensor(1801628.6, shape=(), dtype=float32)
c_loss_3 tf.Tensor(745149.3, shape=(), dtype=float32)

9
s_loss tf.Tensor(611142.0, shape=(), dtype=float32)
c_loss_3 tf.Tensor(547483.25, shape=(), dtype=float32)

10
s_loss tf.Tensor(1162312.8, shape=(), dtype=float32)
c_loss_3 tf.Tensor(728544.6, shape=(), dtype=float32)

11
s_loss tf.Tensor(591470.3, shape=(), dtype=float32)
c_loss_3 tf.Tensor(569579.8, shape=(), dtype=float32)

12
s_loss tf.Tensor(901461.44, shape=(), dtype=float32)
c_loss_3 tf.Tensor(720809.06, shape=(), dtype=float32)

13
s_loss tf.Tensor(514771.75, shape=(), dtype=float32)
c_loss_3 tf.Tensor(583157.94, shape=(), dtype=float32)

14
s_loss tf.Tensor(555082.0, shape=(), dtype=float32)
c_loss_3 tf.Tensor(733099.94, shape=(), dtype=float32)

15
s_loss tf.Tensor(398540.25, shape=(), dtype=float32)
c_loss_3 tf.Tensor(582937.06, shape=(), dtype=float32)

16
s_loss tf.Tensor(1686386.9, shape=(), dtype=float32)
c_loss_3 tf.Tensor(949258.1, shape=(), dtype=float32)

17
s_loss tf.Tensor(374587.2, shape=(), dtype=float32)
c_loss_3 tf.Tensor(616105.7, shape=(), dtype=float32)

18
s_loss tf.Tensor(2503596.8, shape=(), dtype=float32)
c_loss_3 tf.Tensor(907059.4, shape=(), dtype=float32)

19
s_loss tf.Tensor(393780.94, shape=(), dtype=float32)
c_loss_3 tf.Tensor(652435.75, shape=(), dtype=float32)

20
s_loss tf.Tensor(342253.66, shape=(), dtype=float32)
c_loss_3 tf.Tensor(753341.9, shape=(), dtype=float32)

21
s_loss tf.Tensor(285177.38, shape=(), dtype=float32)
c_loss_3 tf.Tensor(630454.25, shape=(), dtype=float32)

22
s_loss tf.Tensor(1861053.6, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1014506.44, shape=(), dtype=float32)

23
s_loss tf.Tensor(227057.23, shape=(), dtype=float32)
c_loss_3 tf.Tensor(648588.5, shape=(), dtype=float32)

24
s_loss tf.Tensor(1769190.8, shape=(), dtype=float32)
c_loss_3 tf.Tensor(969592.8, shape=(), dtype=float32)

25
s_loss tf.Tensor(229794.19, shape=(), dtype=float32)
c_loss_3 tf.Tensor(670500.25, shape=(), dtype=float32)

26
s_loss tf.Tensor(290055.44, shape=(), dtype=float32)
c_loss_3 tf.Tensor(838461.94, shape=(), dtype=float32)

27
s_loss tf.Tensor(437503.03, shape=(), dtype=float32)
c_loss_3 tf.Tensor(615840.3, shape=(), dtype=float32)

28
s_loss tf.Tensor(1828359.6, shape=(), dtype=float32)
c_loss_3 tf.Tensor(963244.9, shape=(), dtype=float32)

29
s_loss tf.Tensor(260726.4, shape=(), dtype=float32)
c_loss_3 tf.Tensor(641311.5, shape=(), dtype=float32)

30
s_loss tf.Tensor(4037012.2, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1081639.5, shape=(), dtype=float32)

31
s_loss tf.Tensor(132063.14, shape=(), dtype=float32)
c_loss_3 tf.Tensor(683507.06, shape=(), dtype=float32)

32
s_loss tf.Tensor(3648797.8, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1086665.0, shape=(), dtype=float32)

33
s_loss tf.Tensor(257858.81, shape=(), dtype=float32)
c_loss_3 tf.Tensor(702107.0, shape=(), dtype=float32)

34
s_loss tf.Tensor(325009.66, shape=(), dtype=float32)
c_loss_3 tf.Tensor(782046.2, shape=(), dtype=float32)

35
s_loss tf.Tensor(526896.75, shape=(), dtype=float32)
c_loss_3 tf.Tensor(676299.1, shape=(), dtype=float32)

36
s_loss tf.Tensor(704477.44, shape=(), dtype=float32)
c_loss_3 tf.Tensor(787919.75, shape=(), dtype=float32)

37
s_loss tf.Tensor(529137.75, shape=(), dtype=float32)
c_loss_3 tf.Tensor(680880.44, shape=(), dtype=float32)

38
s_loss tf.Tensor(783687.94, shape=(), dtype=float32)
c_loss_3 tf.Tensor(799024.75, shape=(), dtype=float32)

39
s_loss tf.Tensor(454358.78, shape=(), dtype=float32)
c_loss_3 tf.Tensor(666126.56, shape=(), dtype=float32)

40
s_loss tf.Tensor(1114407.5, shape=(), dtype=float32)
c_loss_3 tf.Tensor(883184.25, shape=(), dtype=float32)

41
s_loss tf.Tensor(371920.62, shape=(), dtype=float32)
c_loss_3 tf.Tensor(684474.94, shape=(), dtype=float32)

42
s_loss tf.Tensor(1241015.1, shape=(), dtype=float32)
c_loss_3 tf.Tensor(913147.25, shape=(), dtype=float32)

43
s_loss tf.Tensor(378354.22, shape=(), dtype=float32)
c_loss_3 tf.Tensor(701896.5, shape=(), dtype=float32)

44
s_loss tf.Tensor(368677.16, shape=(), dtype=float32)
c_loss_3 tf.Tensor(822711.0, shape=(), dtype=float32)

45
s_loss tf.Tensor(284543.1, shape=(), dtype=float32)
c_loss_3 tf.Tensor(684890.2, shape=(), dtype=float32)

46
s_loss tf.Tensor(2657415.0, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1118634.8, shape=(), dtype=float32)

47
s_loss tf.Tensor(149118.45, shape=(), dtype=float32)
c_loss_3 tf.Tensor(712277.9, shape=(), dtype=float32)

48
s_loss tf.Tensor(2060093.8, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1064177.0, shape=(), dtype=float32)

49
s_loss tf.Tensor(200769.83, shape=(), dtype=float32)
c_loss_3 tf.Tensor(700032.9, shape=(), dtype=float32)

50
s_loss tf.Tensor(1976519.2, shape=(), dtype=float32)
c_loss_3 tf.Tensor(1053871.4, shape=(), dtype=float32)