目录

前言

项目说明

项目结构

数据准备

魔改代码

总结


前言

根据我的另一篇文章:如何将照片美化,DPED机器学习开源项目安装使用 | 机器学习_阿良的博客-CSDN博客

发现DPED项目需要命令化执行且需要图片目录作为处理源。我还是把项目魔改了一下,简化项目结构,合并到一个python代码中。

模型文件比较大,我提供了下载地址,下载后放到项目对应目录即可。

Github仓库地址:github地址

项目说明

项目结构

看一下项目的结构,如下图:

其中模型文件下载地址:https://pan.baidu.com/s/1IUm8xz5dhh8iW_bLWfihPQ 提取码:TUAN

将imagenet-vgg-verydeep-19.mat下载后放在vgg_pretrained目录中。

环境依赖可以直接参考:Python实现替换照片人物背景,精细到头发丝(附上代码) | 机器学习_阿良的博客-CSDN博客

数据准备

我准备了一张测试图如下:

魔改代码

不废话了,上核心代码。

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2021/11/27 13:48
# @Author  : 剑客阿良_ALiang
# @Site    :
# @File    : dped.py# python test_model.py model=iphone_orig dped_dir=dped/ test_subset=full
# iteration=all resolution=orig use_gpu=trueimport imageio
from PIL import Image
import numpy as np
import tensorflow as tf
import os
import sys
import scipy.stats as st
import uuid
from functools import reduce# ---------------------- hy add 2 ----------------------
def log10(x):numerator = tf.compat.v1.log(x)denominator = tf.compat.v1.log(tf.constant(10, dtype=numerator.dtype))return numerator / denominatordef _tensor_size(tensor):from operator import mulreturn reduce(mul, (d.value for d in tensor.get_shape()[1:]), 1)def gauss_kernel(kernlen=21, nsig=3, channels=1):interval = (2 * nsig + 1.) / (kernlen)x = np.linspace(-nsig - interval / 2., nsig + interval / 2., kernlen + 1)kern1d = np.diff(st.norm.cdf(x))kernel_raw = np.sqrt(np.outer(kern1d, kern1d))kernel = kernel_raw / kernel_raw.sum()out_filter = np.array(kernel, dtype=np.float32)out_filter = out_filter.reshape((kernlen, kernlen, 1, 1))out_filter = np.repeat(out_filter, channels, axis=2)return out_filterdef blur(x):kernel_var = gauss_kernel(21, 3, 3)return tf.nn.depthwise_conv2d(x, kernel_var, [1, 1, 1, 1], padding='SAME')def process_command_args(arguments):# specifying default parametersbatch_size = 50train_size = 30000learning_rate = 5e-4num_train_iters = 20000w_content = 10w_color = 0.5w_texture = 1w_tv = 2000dped_dir = 'dped/'vgg_dir = 'vgg_pretrained/imagenet-vgg-verydeep-19.mat'eval_step = 1000phone = ""for args in arguments:if args.startswith("model"):phone = args.split("=")[1]if args.startswith("batch_size"):batch_size = int(args.split("=")[1])if args.startswith("train_size"):train_size = int(args.split("=")[1])if args.startswith("learning_rate"):learning_rate = float(args.split("=")[1])if args.startswith("num_train_iters"):num_train_iters = int(args.split("=")[1])# -----------------------------------if args.startswith("w_content"):w_content = float(args.split("=")[1])if args.startswith("w_color"):w_color = float(args.split("=")[1])if args.startswith("w_texture"):w_texture = float(args.split("=")[1])if args.startswith("w_tv"):w_tv = float(args.split("=")[1])# -----------------------------------if args.startswith("dped_dir"):dped_dir = args.split("=")[1]if args.startswith("vgg_dir"):vgg_dir = args.split("=")[1]if args.startswith("eval_step"):eval_step = int(args.split("=")[1])if phone == "":print("\nPlease specify the camera model by running the script with the following parameter:\n")print("python train_model.py model={iphone,blackberry,sony}\n")sys.exit()if phone not in ["iphone", "sony", "blackberry"]:print("\nPlease specify the correct camera model:\n")print("python train_model.py model={iphone,blackberry,sony}\n")sys.exit()print("\nThe following parameters will be applied for CNN training:\n")print("Phone model:", phone)print("Batch size:", batch_size)print("Learning rate:", learning_rate)print("Training iterations:", str(num_train_iters))print()print("Content loss:", w_content)print("Color loss:", w_color)print("Texture loss:", w_texture)print("Total variation loss:", str(w_tv))print()print("Path to DPED dataset:", dped_dir)print("Path to VGG-19 network:", vgg_dir)print("Evaluation step:", str(eval_step))print()return phone, batch_size, train_size, learning_rate, num_train_iters, \w_content, w_color, w_texture, w_tv, \dped_dir, vgg_dir, eval_stepdef process_test_model_args(arguments):phone = ""dped_dir = 'dped/'test_subset = "small"iteration = "all"resolution = "orig"use_gpu = "true"for args in arguments:if args.startswith("model"):phone = args.split("=")[1]if args.startswith("dped_dir"):dped_dir = args.split("=")[1]if args.startswith("test_subset"):test_subset = args.split("=")[1]if args.startswith("iteration"):iteration = args.split("=")[1]if args.startswith("resolution"):resolution = args.split("=")[1]if args.startswith("use_gpu"):use_gpu = args.split("=")[1]if phone == "":print("\nPlease specify the model by running the script with the following parameter:\n")print("python test_model.py model={iphone,blackberry,sony,iphone_orig,blackberry_orig,sony_orig}\n")sys.exit()return phone, dped_dir, test_subset, iteration, resolution, use_gpudef get_resolutions():# IMAGE_HEIGHT, IMAGE_WIDTHres_sizes = {}res_sizes["iphone"] = [1536, 2048]res_sizes["iphone_orig"] = [1536, 2048]res_sizes["blackberry"] = [1560, 2080]res_sizes["blackberry_orig"] = [1560, 2080]res_sizes["sony"] = [1944, 2592]res_sizes["sony_orig"] = [1944, 2592]res_sizes["high"] = [1260, 1680]res_sizes["medium"] = [1024, 1366]res_sizes["small"] = [768, 1024]res_sizes["tiny"] = [600, 800]return res_sizesdef get_specified_res(res_sizes, phone, resolution):if resolution == "orig":IMAGE_HEIGHT = res_sizes[phone][0]IMAGE_WIDTH = res_sizes[phone][1]else:IMAGE_HEIGHT = res_sizes[resolution][0]IMAGE_WIDTH = res_sizes[resolution][1]IMAGE_SIZE = IMAGE_WIDTH * IMAGE_HEIGHT * 3return IMAGE_HEIGHT, IMAGE_WIDTH, IMAGE_SIZEdef extract_crop(image, resolution, phone, res_sizes):if resolution == "orig":return imageelse:x_up = int((res_sizes[phone][1] - res_sizes[resolution][1]) / 2)y_up = int((res_sizes[phone][0] - res_sizes[resolution][0]) / 2)x_down = x_up + res_sizes[resolution][1]y_down = y_up + res_sizes[resolution][0]return image[y_up: y_down, x_up: x_down, :]# ---------------------- hy add 1 ----------------------
def resnet(input_image):with tf.compat.v1.variable_scope("generator"):W1 = weight_variable([9, 9, 3, 64], name="W1")b1 = bias_variable([64], name="b1")c1 = tf.nn.relu(conv2d(input_image, W1) + b1)# residual 1W2 = weight_variable([3, 3, 64, 64], name="W2")b2 = bias_variable([64], name="b2")c2 = tf.nn.relu(_instance_norm(conv2d(c1, W2) + b2))W3 = weight_variable([3, 3, 64, 64], name="W3")b3 = bias_variable([64], name="b3")c3 = tf.nn.relu(_instance_norm(conv2d(c2, W3) + b3)) + c1# residual 2W4 = weight_variable([3, 3, 64, 64], name="W4")b4 = bias_variable([64], name="b4")c4 = tf.nn.relu(_instance_norm(conv2d(c3, W4) + b4))W5 = weight_variable([3, 3, 64, 64], name="W5")b5 = bias_variable([64], name="b5")c5 = tf.nn.relu(_instance_norm(conv2d(c4, W5) + b5)) + c3# residual 3W6 = weight_variable([3, 3, 64, 64], name="W6")b6 = bias_variable([64], name="b6")c6 = tf.nn.relu(_instance_norm(conv2d(c5, W6) + b6))W7 = weight_variable([3, 3, 64, 64], name="W7")b7 = bias_variable([64], name="b7")c7 = tf.nn.relu(_instance_norm(conv2d(c6, W7) + b7)) + c5# residual 4W8 = weight_variable([3, 3, 64, 64], name="W8")b8 = bias_variable([64], name="b8")c8 = tf.nn.relu(_instance_norm(conv2d(c7, W8) + b8))W9 = weight_variable([3, 3, 64, 64], name="W9")b9 = bias_variable([64], name="b9")c9 = tf.nn.relu(_instance_norm(conv2d(c8, W9) + b9)) + c7# ConvolutionalW10 = weight_variable([3, 3, 64, 64], name="W10")b10 = bias_variable([64], name="b10")c10 = tf.nn.relu(conv2d(c9, W10) + b10)W11 = weight_variable([3, 3, 64, 64], name="W11")b11 = bias_variable([64], name="b11")c11 = tf.nn.relu(conv2d(c10, W11) + b11)# FinalW12 = weight_variable([9, 9, 64, 3], name="W12")b12 = bias_variable([3], name="b12")enhanced = tf.nn.tanh(conv2d(c11, W12) + b12) * 0.58 + 0.5return enhanceddef adversarial(image_):with tf.compat.v1.variable_scope("discriminator"):conv1 = _conv_layer(image_, 48, 11, 4, batch_nn=False)conv2 = _conv_layer(conv1, 128, 5, 2)conv3 = _conv_layer(conv2, 192, 3, 1)conv4 = _conv_layer(conv3, 192, 3, 1)conv5 = _conv_layer(conv4, 128, 3, 2)flat_size = 128 * 7 * 7conv5_flat = tf.reshape(conv5, [-1, flat_size])W_fc = tf.Variable(tf.compat.v1.truncated_normal([flat_size, 1024], stddev=0.01))bias_fc = tf.Variable(tf.constant(0.01, shape=[1024]))fc = leaky_relu(tf.matmul(conv5_flat, W_fc) + bias_fc)W_out = tf.Variable(tf.compat.v1.truncated_normal([1024, 2], stddev=0.01))bias_out = tf.Variable(tf.constant(0.01, shape=[2]))adv_out = tf.nn.softmax(tf.matmul(fc, W_out) + bias_out)return adv_outdef weight_variable(shape, name):initial = tf.compat.v1.truncated_normal(shape, stddev=0.01)return tf.Variable(initial, name=name)def bias_variable(shape, name):initial = tf.constant(0.01, shape=shape)return tf.Variable(initial, name=name)def conv2d(x, W):return tf.nn.conv2d(x, W, strides=[1, 1, 1, 1], padding='SAME')def leaky_relu(x, alpha=0.2):return tf.maximum(alpha * x, x)def _conv_layer(net, num_filters, filter_size, strides, batch_nn=True):weights_init = _conv_init_vars(net, num_filters, filter_size)strides_shape = [1, strides, strides, 1]bias = tf.Variable(tf.constant(0.01, shape=[num_filters]))net = tf.nn.conv2d(net, weights_init, strides_shape, padding='SAME') + biasnet = leaky_relu(net)if batch_nn:net = _instance_norm(net)return netdef _instance_norm(net):batch, rows, cols, channels = [i.value for i in net.get_shape()]var_shape = [channels]mu, sigma_sq = tf.compat.v1.nn.moments(net, [1, 2], keepdims=True)shift = tf.Variable(tf.zeros(var_shape))scale = tf.Variable(tf.ones(var_shape))epsilon = 1e-3normalized = (net - mu) / (sigma_sq + epsilon) ** (.5)return scale * normalized + shiftdef _conv_init_vars(net, out_channels, filter_size, transpose=False):_, rows, cols, in_channels = [i.value for i in net.get_shape()]if not transpose:weights_shape = [filter_size, filter_size, in_channels, out_channels]else:weights_shape = [filter_size, filter_size, out_channels, in_channels]weights_init = tf.Variable(tf.compat.v1.truncated_normal(weights_shape,stddev=0.01,seed=1),dtype=tf.float32)return weights_init# ---------------------- hy add 0 ----------------------def beautify(pic_path: str, output_dir: str, gpu='1'):tf.compat.v1.disable_v2_behavior()# process command argumentsphone = "iphone_orig"test_subset = "full"iteration = "all"resolution = "orig"# get all available image resolutionsres_sizes = get_resolutions()# get the specified image resolutionIMAGE_HEIGHT, IMAGE_WIDTH, IMAGE_SIZE = get_specified_res(res_sizes, phone, resolution)if gpu == '1':use_gpu = 'true'else:use_gpu = 'false'# disable gpu if specifiedconfig = tf.compat.v1.ConfigProto(device_count={'GPU': 0}) if use_gpu == "false" else None# create placeholders for input imagesx_ = tf.compat.v1.placeholder(tf.float32, [None, IMAGE_SIZE])x_image = tf.reshape(x_, [-1, IMAGE_HEIGHT, IMAGE_WIDTH, 3])# generate enhanced imageenhanced = resnet(x_image)with tf.compat.v1.Session(config=config) as sess:# test_dir = dped_dir + phone.replace("_orig",#                                     "") + "/test_data/full_size_test_images/"# test_photos = [f for f in os.listdir(#     test_dir) if os.path.isfile(test_dir + f)]test_photos = [pic_path]if test_subset == "small":# use five first images onlytest_photos = test_photos[0:5]if phone.endswith("_orig"):# load pre-trained modelsaver = tf.compat.v1.train.Saver()saver.restore(sess, "models_orig/" + phone)for photo in test_photos:# load training image and crop it if necessarynew_pic_name = uuid.uuid4()print("Testing original " +phone.replace("_orig","") +" model, processing image " +photo)image = np.float16(np.array(Image.fromarray(imageio.imread(photo)).resize([res_sizes[phone][1], res_sizes[phone][0]]))) / 255image_crop = extract_crop(image, resolution, phone, res_sizes)image_crop_2d = np.reshape(image_crop, [1, IMAGE_SIZE])# get enhanced imageenhanced_2d = sess.run(enhanced, feed_dict={x_: image_crop_2d})enhanced_image = np.reshape(enhanced_2d, [IMAGE_HEIGHT, IMAGE_WIDTH, 3])before_after = np.hstack((image_crop, enhanced_image))photo_name = photo.rsplit(".", 1)[0]# save the results as .png images# imageio.imwrite(#     "visual_results/" +#     phone +#     "_" +#     photo_name +#     "_enhanced.png",#     enhanced_image)imageio.imwrite(os.path.join(output_dir, '{}.png'.format(new_pic_name)), enhanced_image)# imageio.imwrite(#     "visual_results/" +#     phone +#     "_" +#     photo_name +#     "_before_after.png",#     before_after)imageio.imwrite(os.path.join(output_dir, '{}_before_after.png'.format(new_pic_name)), before_after)return os.path.join(output_dir, '{}.png'.format(new_pic_name))else:num_saved_models = int(len([f for f in os.listdir("models_orig/") if f.startswith(phone + "_iteration")]) / 2)if iteration == "all":iteration = np.arange(1, num_saved_models) * 1000else:iteration = [int(iteration)]for i in iteration:# load pre-trained modelsaver = tf.compat.v1.train.Saver()saver.restore(sess,"models_orig/" +phone +"_iteration_" +str(i) +".ckpt")for photo in test_photos:# load training image and crop it if necessarynew_pic_name = uuid.uuid4()print("iteration " + str(i) + ", processing image " + photo)image = np.float16(np.array(Image.fromarray(imageio.imread(photo)).resize([res_sizes[phone][1], res_sizes[phone][0]]))) / 255image_crop = extract_crop(image, resolution, phone, res_sizes)image_crop_2d = np.reshape(image_crop, [1, IMAGE_SIZE])# get enhanced imageenhanced_2d = sess.run(enhanced, feed_dict={x_: image_crop_2d})enhanced_image = np.reshape(enhanced_2d, [IMAGE_HEIGHT, IMAGE_WIDTH, 3])before_after = np.hstack((image_crop, enhanced_image))photo_name = photo.rsplit(".", 1)[0]# save the results as .png images# imageio.imwrite(#     "visual_results/" +#     phone +#     "_" +#     photo_name +#     "_iteration_" +#     str(i) +#     "_enhanced.png",#     enhanced_image)imageio.imwrite(os.path.join(output_dir, '{}.png'.format(new_pic_name)), enhanced_image)# imageio.imwrite(#     "visual_results/" +#     phone +#     "_" +#     photo_name +#     "_iteration_" +#     str(i) +#     "_before_after.png",#     before_after)imageio.imwrite(os.path.join(output_dir, '{}_before_after.png'.format(new_pic_name)), before_after)return os.path.join(output_dir, '{}.png'.format(new_pic_name))if __name__ == '__main__':print(beautify('C:/Users/yi/Desktop/6.jpg', 'result/'))

代码说明

1、beautify方法有3个参数,分别为图片地址、输出目录、是否使用gpu(默认使用)。

2、输出的图片有两张,为了文件名不重复,使用uuid作为文件名,后缀带_before_after为对比图。

3、没有对文件做校验,如果需要可以自行添加。

验证一下效果

怎么样?很炫吧。

总结

研究这个项目还是很有意思的,记录与分享又是另一种快乐。以前以为自己是个开朗的人,现在细细翻阅自己的人生,更多的是宁静与孤独。以前曾看书看马尔克斯的一句话:在变老的路上,与其抗拒孤独,不如学会享受孤独。所以孤独没什么不好的,沉浸在程序的另一个世界里,就是另一个心情。

分享:

生命从来不曾离开过孤独而独立存在。无论是我们出生、我们成长、我们相爱还是我们成功失败,直到最后的最后,孤独犹如影子一样存在于生命一隅。——《马尔克斯》

如果本文对你有用的话,请点个赞吧,谢谢!

Python实现图片美化,醉后不知天在水?(附上代码) | 机器学习相关推荐

  1. Contelec KL750-5K0/M-SE醉后不知天在水

    醉后不知天在水,满船清梦压星河 我终于又回到西溪,躺在茭芦田庄的床上,看着窗外庭院里熟悉的风景,还有枝丫上的初春. 一切都是那么美好,走在西溪的路上,吹面而来的风雨.就连空气都是温柔的. 西溪之于我, ...

  2. python做图片美化_python图片美化

    广告关闭 腾讯云11.11云上盛惠 ,精选热门产品助力上云,云服务器首年88元起,买的越多返的越多,最高返5000元! 功能性是开发的第一要务每一个 python 图形界面库都有它自有的功能特性和界面 ...

  3. python做图片美化_Python实现简单的照片磨皮(照片智能磨皮) 最新免费版

    Python实现简单的照片磨皮(照片智能磨皮)是一款用python写的最好的照片磨皮软件.需要配置opencv和numpy,使用的时候地址需要加英文的引号,斜杠要用双斜杠,例如"D:\\a. ...

  4. python做图片美化_如何美化MATLAB和Python画出来的图

    如何美化MATLAB和Python画出来的图 写在前面 俗话有句叫做:字不如表,表不如图,意思就是图可以最直观最显然的表达我们想要表达的信息,其升降趋势一目了然:表其次,能够看到数值,但是想要看出变化 ...

  5. python做图片美化软件_Python大数据分析2:图形样式的美化

    图形最初显示的样式往往并非十分好看,我们可以通过大量的设置为完善图形的显示.事实上,matplotlib样式设置功能非常强大,因此在这里我们也主要结合一些最为常见的功能来做介绍. 比如我们想改变线性图 ...

  6. python获取图片坐标_python提取照片坐标信息的实例代码

    python提取照片坐标信息的代码如下所示: from PIL import Image from PIL.ExifTags import TAGS import os output="Z: ...

  7. SCU - 4572 醉后不知天在水,满船清梦压星河【思维】

    传送门 题意: 在自然数序列中 (0,1,2,3,4,5-.),求去掉所有含2,3,5,7的数字后 (0,1,4,6,8,9-)的第k个数. 思路: 这道题就很有意思啦.. 去掉后我们可以发现从小到大 ...

  8. 醉后不知天在水,满船清梦压星河。—第三十六天

  9. 醉后不知天在水 满船清梦压星河。—第二十一天

  10. 简单使用python将图片转换为字符画

    将图片转换为字符码的形式相信大家都有见过. 记得小编以前看到这些的时候是极其羡慕的,也很渴望能够实现这项功能. 然后将一副画转换为这样的字符画,发给周围的朋友炫耀. NH HN–: !;;– –;;; ...

最新文章

  1. SpringMVC中重定向
  2. 如何在CentOS 5/6上安装EPEL源
  3. python ctime函数_Python time 模块
  4. php读取图片输出,php读取图片流输出到页面图片
  5. 项目中用到的ws2811炫彩灯控制程序
  6. 人人网主页登录_人人网回归,你的前任和全部黑历史将被翻开!买账吗?
  7. Java程序员怎么规划五年职业生涯
  8. 百度C++工程师的那些极限优化(内存篇)
  9. redis踩坑:redis哨兵开启了保护模式导致主从切换不同步
  10. DPDK Rx flexible descriptor在Intel E810网卡中的使用
  11. ITRON同步和通信管理
  12. 河南信息统计学院微信公众平台API汇总
  13. Mysql中INSTANT使用
  14. 极限学习机(Extreme Learning Machine)(小白之路)
  15. 剑网3服务器一直显示维护,8月3日例行维护完毕 服务器已正常开启
  16. iOS 内购的最新讲解
  17. 币圈神话的成就者,谷歌团队首发PlusFo
  18. Openmeetings开源视频部署
  19. linux下创建用户6,Linux 用户管理
  20. Mac出现问题的5个警告信号与处理方法

热门文章

  1. snmpwalk工具使用
  2. 《认知天性》:讲述基于科学的学习方法
  3. Git版本控制管理(一)--安装
  4. 三次hermite插值多项式例题_2点三次Hermite插值多项式解析.ppt
  5. grads 相关系数_GrADS实习报告6
  6. jspstudy启动mysql失败_mysql服务启动失败解决方案
  7. ESP8266使用入门教程
  8. Tomcat 修改启动端口号
  9. 程序设计原则之SOLID原则
  10. C/C++语言IDE_开发工具