{"id":2508,"date":"2020-02-07T21:28:57","date_gmt":"2020-02-07T12:28:57","guid":{"rendered":"https:\/\/julialang.kr\/?p=2508"},"modified":"2020-02-07T21:32:23","modified_gmt":"2020-02-07T12:32:23","slug":"flux-cifar10-upgraded-example","status":"publish","type":"post","link":"https:\/\/julialang.kr\/?p=2508","title":{"rendered":"[Flux] cifar10 upgraded example"},"content":{"rendered":"\n<p>\uc774\uc804 cifar10 example\uc5d0\uc11c \ubaa8\ub378\uc744 \uc800\uc7a5\ud558\uace0 \uc77d\uc5b4\uc624\ub294 \ubd80\ubd84\uc744 \ucd94\uac00 \ud558\uace0 , \uc678\ubd80 \ud30c\ub77c\ubbf8\ud130\ub97c \uc785\ub825 \ubc1b\uc544 \ubc18\uc601 \ud558\ub294 \uad6c\uc870\ub85c \ubcc0\uacbd \ud558\uc600\ub2e4.<\/p>\n\n\n\n<ol><li>training\ud55c model\uc744 \uc800\uc7a5\ud558\uace0 \uc77d\uae30 \uae30\ub2a5\uc744 \ucd94\uac00 \ud558\uc5ec \uc774\uc5b4\uc11c training\uc744 \ud560 \uc218 \uc788\uac8c \ud588\ub2e4<\/li><li>epoch, batch size, \uc800\uc7a5\ub41c model \ud30c\uc77c \ub85c\ub529 \uc5ec\ubd80,\ub85c\uadf8\ub97c \ud654\uba74 \ub610\ub294 \ud30c\uc77c\ub85c \uc800\uc7a5, gpu device , gpu device \ub97c \uc120\ud0dd \ud560 \uc218 \uc788\uac8c \ud588\ub2e4.<\/li><li>\ubaa8\ub378 \uc800\uc7a5\uc2dc cpu \ubaa8\ub4dc\ub85c \ubaa8\ub378\uc744 \uc804\ud658 \ud558\uc5ec \uc800\uc7a5\ud574\uc57c \ud55c\ub2e4. gpu\ubaa8\ub4dc\ub85c \uc800\uc7a5\ud558\ub294 \uacbd\uc6b0 \ubaa8\ub378\uc774 \uc7ac\ub300\ub85c \uc800\uc7a5\ub418\uc9c0 \uc54a\uace0 loading\uc2dc \ubb38\uc81c\uac00 \ub428<\/li><\/ol>\n\n\n\n<p>\uc0ac\uc6a9\uc608\uc2dc<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>julia cifar10_gpu_minibatch.jl -e 100 -b 100 -g 3 -m true -l true<\/code><\/pre>\n\n\n\n<p>cifar10_gpu_minibatch.jl<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>#=\n cifar10 dataset spec\n - 60,000 images of 32x32 size \n - train images : 50,000\n - test images : 10,000\n - classify item : 10\n - each class have 6,000 images and 5,000 train images, 1,000 test images\n \n Data format:\n WHCN order : (width, height, #channels, #batches)\n ex) A single 100x100 RGB image data format : 100x100x3x1\n =#\n\n# Julia version : 1.3.1\n# Flux version : v0.10.1\n__precompile__(true)\nusing Random\nusing BSON\nusing BSON: @save,@load\nusing Logging\nusing Dates\nusing NNlib \nusing CuArrays\nusing CUDAdrv\nusing CUDAnative: device!\nusing Flux, Metalhead, Statistics\nusing Flux: onehotbatch, onecold, crossentropy, throttle\nusing Metalhead: trainimgs\nusing Images: channelview\nusing Statistics: mean\nusing Base.Iterators: partition\nusing ArgParse\n#=\nArgument parsing \n=#\n\nfunction parse_commandline()\n    s = ArgParseSettings()\n    @add_arg_table s begin\n        \"--epoch\",\"-e\"\n            help = \"epoch number, default=30\"\n            arg_type = Int\n            default = 30\n        \"--batch\", \"-b\"\n            help = \"mini-batch size, default=200\"\n            arg_type = Int\n            default = 100\n        \"--gpu\", \"-g\"\n            help = \"gpu index to use , 0,1,2,3,.., default=0\"\n            arg_type = Int\n            default = 0\n        \"--model\", \"-m\"\n            help = \"use saved model file\"\n            arg_type = Bool\n            default = true\n        \"--log\",\"-l\"\n            help = \"create log file\"\n            arg_type = Bool\n            default = true            \n    end\n\n    return parse_args(s)\nend\nparsed_args = parse_commandline()\n\nepochs = parsed_args[\"epoch\"]\nbatch_size = parsed_args[\"batch\"]\nuse_saved_model = parsed_args[\"model\"]\ngpu_device = parsed_args[\"gpu\"]\ncreate_log_file = parsed_args[\"log\"]\n\nif create_log_file\n  log_file =\".\/cifar10_vgg16_$(Dates.format(now(),\"yyyymmdd-HHMMSS\")).log\"\n  log = open(log_file, \"w+\")\nelse\n  log = stdout\nend\nglobal_logger(ConsoleLogger(log))\n\n@info \"Start - $(now())\";flush(log)\n\n\n@info \"=============== Arguments ===============\"\n@info \"epochs=$(epochs)\"\n@info \"batch_size=$(batch_size)\"\n@info \"use_saved_model=$(use_saved_model)\"\n@info \"gpu_device=$(gpu_device)\"\n@info \"=========================================\";flush(log)\n\nconst model_file = \".\/cifar10_vgg16_model.bson\"\n\n# Very important : this prevent loss NaN\nconst \u03f5 = 1.0f-10\n\n\n# use 1nd GPU : default\n#CUDAnative.device!(0)\ndevice!(gpu_device)\nCuArrays.allowscalar(false)\n\n@info \"Config VGG16, VGG19 models ...\";flush(log)\n\nif use_saved_model &amp;&amp; isfile(model_file)\n  # flush : \ubc84\ud37c\ub9c1 \uc5c6\uc774 \uc989\uac01 log\ub97c \ud30c\uc77c \ub610\ub294 console\uc5d0 write\ud558\ub3c4\ub85d \ud568\n  @info \"Load saved model $(model_file) ...\";flush(log)\n  # model : @save\uc2dc \uc0ac\uc6a9\ud55c object\uba85\n  @load model_file model\n  m = model |> gpu\nelse\n  @info \"Create new model ...\";flush(log)\n  # VGG16 and VGG19 models\n  vgg16() = Chain(\n    Conv((3, 3), 3 => 64, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(64),\n    Conv((3, 3), 64 => 64, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(64),\n    MaxPool((2,2)),\n    Conv((3, 3), 64 => 128, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(128),\n    Conv((3, 3), 128 => 128, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(128),\n    MaxPool((2,2)),\n    Conv((3, 3), 128 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    Conv((3, 3), 256 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    Conv((3, 3), 256 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    MaxPool((2,2)),\n    Conv((3, 3), 256 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    MaxPool((2,2)),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    MaxPool((2,2)),\n    x -> reshape(x, :, size(x, 4)),\n    Dense(512, 4096, relu),\n    Dropout(0.5),\n    Dense(4096, 4096, relu),\n    Dropout(0.5),\n    Dense(4096, 10),\n    softmax)\n\n  vgg19() = Chain(\n    Conv((3, 3), 3 => 64, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(64),\n    Conv((3, 3), 64 => 64, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(64),\n    MaxPool((2,2)),\n    Conv((3, 3), 64 => 128, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(128),\n    Conv((3, 3), 128 => 128, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(128),\n    MaxPool((2,2)),\n    Conv((3, 3), 128 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    Conv((3, 3), 256 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    Conv((3, 3), 256 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(256),\n    Conv((3, 3), 256 => 256, relu, pad=(1, 1), stride=(1, 1)),\n    MaxPool((2,2)),\n    Conv((3, 3), 256 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    MaxPool((2,2)),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    BatchNorm(512),\n    Conv((3, 3), 512 => 512, relu, pad=(1, 1), stride=(1, 1)),\n    MaxPool((2,2)),\n    x -> reshape(x, :, size(x, 4)),\n    Dense(512, 4096, relu),\n    Dropout(0.5),\n    Dense(4096, 4096, relu),\n    Dropout(0.5),\n    Dense(4096, 10),\n    softmax)\n    \n  m = vgg16() |> gpu    \nend\n# \n# Function to convert the RGB image to Float64 Arrays\n#=\n1)channelview\ub85c \uc774\ubbf8\uc9c0\uc758 color\ub97c channel\ubcc4\ub85c \ubd84\ub9ac\ud55c\ub2e4.\n- \ubd84\ub9ac\ub41c channel\uc740 \ub9e8\uc55e\uc5d0 \uc0c8\ub85c\uc6b4 \ucc28\uc6d0\uc744 \ucd94\uac00 \ud558\uc5ec channel\uc744 \ubd84\ub9ac\ud55c\ub2e4.\n- \uc608) 32x32 \uc774\ubbf8\uc9c0\uc758 \ucc44\ub110\uc744 \ubd84\ub9ac\ud558\uba74 3x32x32\ub85c 3\uac1c\uc758 \ucc44\ub110\uc774 \ucd94\uac00 \ub41c\ub2e4\n2)permutedims\ub85c \ubd84\ub9ac\ub41c \ucc44\ub110\uc744 \ub4a4\ub85c \ubcf4\ub0b8\ub2e4.\n- Flux\uc5d0\uc11c \uc0ac\uc6a9\ub418\ub294 \uc774\ubbf8\uc9c0 \ud3ec\ub9f7\uc740 WHCN-width,height,#channel,#batches \uc774\ub2e4\n- \ucc44\ub110\ubd84\ub9ac\ub41c \uc774\ubbf8\uc9c0\uac00 3x32x32\uc778 \uacbd\uc6b0 permutedims(img,(2,3,1))\uc744 \uc801\uc6a9\ud558\uba74\n- 32x32x3\uc73c\ub85c width,height,#channel \uc21c\uc73c\ub85c \ubc14\ub010\ub2e4.\n=#\ngetarray(X) = Float32.(permutedims(channelview(X), (2, 3, 1)))\n\n\n@info \"Data download and preparing ...\";flush(log)\nfunction make_minibatch(imgs,labels,batch_size)\n  data_set = [(cat(imgs[i]..., dims = 4) |> gpu, \n          labels[:,i]) |> gpu \n          for i in partition(1:length(imgs), batch_size)]\n  return data_set\nend\n# Fetching the train and validation data and getting them into proper shape\n#=\ntrainimgs(\ubaa8\ub4c8\uba85) : \n - \ubaa8\ub4c8\uba85\uc774 \ub4e4\uc5b4 \uac00\uba74 \ubaa8\ub4c8\uba85\uc5d0 \uad00\ub828\ub41c train\uc6a9 \ub370\uc774\ud130\ub97c \ub2e4\uc6b4\ubc1b\uc544 \ub9ac\ud134\ud55c\ub2e4.\n - ex) trainimgs(CIFAR10) : 50,000\uac1c\uc758 train data\uac00 return \ub41c\ub2e4.\nX \n=#\n\nX = trainimgs(CIFAR10)\n# Training\uc6a9 \ub370\uc774\ud130 \uc900\ube44\n# \uc774\ubbf8\uc9c0 \ucc44\ub110 \ubd84\ub9ac \ubc0f \uc7ac\ubc30\uc5f4, training\uc6a9\uc73c\ub85c 60,000\uac1c\uc911 50,000\uac1c\ub97c \uc0ac\uc6a9\ud55c\ub2e4.\ntrain_idxs = 1:49000\ntrain_imgs = [getarray(X[i].img) for i in train_idxs]\ntrain_labels = float.(onehotbatch([X[i].ground_truth.class for i in train_idxs],1:10))\ntrain_dataset = make_minibatch(train_imgs,train_labels,batch_size)\n\nvalid_idxs = 49001:50000\nvalX = cat([getarray(X[i].img) for i in valid_idxs]..., dims = 4) |> gpu\nvalY = float.(onehotbatch([X[i].ground_truth.class for i in valid_idxs],1:10)) |> gpu\n\n# Defining the loss and accuracy functions\n\n@info \"VGG16 models instantiation ...\";flush(log)\n\nloss(x, y) = crossentropy(m(x) .+ \u03f5, y .+ \u03f5)\n\naccuracy(x, y) = mean(onecold(m(x)|>cpu, 1:10) .== onecold(y|>cpu, 1:10))\n\n# Defining the callback and the optimizer\n\nevalcb = throttle(() -> @info(accuracy(valX, valY)), 10)\n\nopt = ADAM()\n\n@info \"Training model...\";flush(log)\n\n# used for plots\n# accs = Array{Float32}(undef,0)\n@time begin\ndataset_len = length(train_dataset)\nshuffle_idxs = collect(1:dataset_len)\nshuffle!(shuffle_idxs)\nfor i in 1:epochs\n  for (idx,data_idx) in enumerate(shuffle_idxs)\n    dataset = train_dataset[data_idx]\n    Flux.train!(loss,params(m),[dataset],opt)\n    #Flux.train!(loss,params(m),[dataset],opt,cb = evalcb)    \n    acc = accuracy(valX,valY)\n    @info \"Epoch# $(i)\/$(epochs) - #$(idx)\/$(dataset_len) loss: $(loss(dataset...)), accuracy: $(acc)\";flush(log)\n    # push!(accs,acc)\n  end\n  model = m |> cpu  \n  # @load \uc2dc \uc5ec\uae30\uc5d0\uc11c \uc0ac\uc6a9\ud55c \"model\" \ub85c \ub85c\ub529 \ud574\uc57c \ud568\n  @save model_file model\nend\nend # end of @time\n# Fetch the test data from Metalhead and get it into proper shape.\n# CIFAR-10 does not specify a validation set so valimgs fetch the testdata instead of testimgs\ntX = valimgs(CIFAR10)\ntest_idxs = 1:10000\ntest_imgs = [getarray(tX[i].img) for i in test_idxs]\ntest_labels = float.(onehotbatch([tX[i].ground_truth.class for i in test_idxs], 1:10))\ntest_dataset = make_minibatch(test_imgs,test_labels,batch_size)\n\ntest_accs = Array{Float32}(undef,0)\ndataset_len = length(test_dataset)\nfor (idx,dataset) in enumerate(test_dataset)\n  acc = accuracy(dataset...)\n  push!(test_accs,acc)\nend\n@info \"Test accuracy : $(mean(test_accs))\"\n@info \"End - $(now())\"\nclose(log)\n\n<\/code><\/pre>\n","protected":false},"excerpt":{"rendered":"<p>\uc774\uc804 cifar10 example\uc5d0\uc11c \ubaa8\ub378\uc744 \uc800\uc7a5\ud558\uace0 \uc77d\uc5b4\uc624\ub294 \ubd80\ubd84\uc744 \ucd94\uac00 \ud558\uace0 , \uc678\ubd80 \ud30c\ub77c\ubbf8\ud130\ub97c \uc785\ub825 \ubc1b\uc544 \ubc18\uc601 \ud558\ub294 \uad6c\uc870\ub85c \ubcc0\uacbd \ud558\uc600\ub2e4. training\ud55c model\uc744 \uc800\uc7a5\ud558\uace0 \uc77d\uae30 \uae30\ub2a5\uc744 \ucd94\uac00 \ud558\uc5ec \uc774\uc5b4\uc11c training\uc744 \ud560 \uc218 \uc788\uac8c \ud588\ub2e4 epoch, batch size, \uc800\uc7a5\ub41c model \ud30c\uc77c \ub85c\ub529 \uc5ec\ubd80,\ub85c\uadf8\ub97c \ud654\uba74 \ub610\ub294 \ud30c\uc77c\ub85c \uc800\uc7a5, gpu device , gpu device \ub97c \uc120\ud0dd \ud560 \uc218 \uc788\uac8c \ud588\ub2e4. [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"site-sidebar-layout":"default","site-content-layout":"default","ast-site-content-layout":"","site-content-style":"default","site-sidebar-style":"default","ast-global-header-display":"","ast-banner-title-visibility":"","ast-main-header-display":"","ast-hfb-above-header-display":"","ast-hfb-below-header-display":"","ast-hfb-mobile-header-display":"","site-post-title":"","ast-breadcrumbs-content":"","ast-featured-img":"","footer-sml-layout":"","theme-transparent-header-meta":"default","adv-header-id-meta":"","stick-header-meta":"","header-above-stick-meta":"","header-main-stick-meta":"","header-below-stick-meta":"","astra-migrate-meta-layouts":"default","ast-page-background-enabled":"default","ast-page-background-meta":{"desktop":{"background-color":"","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"tablet":{"background-color":"","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"mobile":{"background-color":"","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""}},"ast-content-background-meta":{"desktop":{"background-color":"var(--ast-global-color-5)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"tablet":{"background-color":"var(--ast-global-color-5)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"mobile":{"background-color":"var(--ast-global-color-5)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""}},"footnotes":""},"categories":[18,21],"tags":[],"_links":{"self":[{"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/posts\/2508"}],"collection":[{"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/julialang.kr\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=2508"}],"version-history":[{"count":3,"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/posts\/2508\/revisions"}],"predecessor-version":[{"id":2511,"href":"https:\/\/julialang.kr\/index.php?rest_route=\/wp\/v2\/posts\/2508\/revisions\/2511"}],"wp:attachment":[{"href":"https:\/\/julialang.kr\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=2508"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/julialang.kr\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=2508"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/julialang.kr\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=2508"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}