这次先看tenforflow_infer.py
1.打开anaconda navigator>打开spyder(记得装)
2.file>open>选择目录>打开.py文件
3.初步分块理解代码
import cv2
import time
import argparse
加载一些模块。其中cv2模块的用法参考:https://www.cnblogs.com/shizhengwen/p/8719062.html
import numpy as np
from PIL import Image
from keras.models import model_from_json
from utils.anchor_generator import generate_anchors
from utils.anchor_decode import decode_bbox
from utils.nms import single_class_non_max_suppression
from load_model.tensorflow_loader import load_tf_model, tf_inference
*1 NumPy函数库是Python开发环境的一个独立模块,是Python的一种开源的数值计算扩展工具。import numpy as np即导入函数库
*2 from……import含义是 把一个模块中所有函数都导入进来
所以是把PIL模块里的Image函数导进来
*3 模型的权重保存在HDF5中/模型的结构保存在JSON文件或者YAML文件中
model.to_json() 以 JSON 字符串的形式返回模型的表示(Keras提供了to_json()生成模型JSON描述,并将模型的JSON描述保存到文件中)。请注意,该表示不包括权重,仅包含结构。
反序列化时候,通过model_from_json()函数加载模型描述,编译生成模型
*4 generate_anchors函数的功能对应faster R-CNN中anchors 的生成
https://zhuanlan.zhihu.com/p/102978748?utm_source=wechat_session参考资料
因为SSD算法借鉴Faster R-CNN算法的Anchor机制,所以这里导入该函数
*5 待理解从名字上看应该是Default box的 计算
*6 后处理使用NMS,应该是非最大值抑制算的有关函数
*7涉及模块的加载与保存
具体函数的作用应该要去查看每个源代码才能得知,这个一步步来,所有要用到的代码都在子目录下
sess, graph = load_tf_model('models/face_mask_detection.pb')
# anchor configuration
feature_map_sizes = [[33, 33], [17, 17], [9, 9], [5, 5], [3, 3]]
anchor_sizes = [[0.04, 0.056], [0.08, 0.11], [0.16, 0.22], [0.32, 0.45], [0.64, 0.72]]
anchor_ratios = [[1, 0.62, 0.42]] * 5
# generate anchors
anchors = generate_anchors(feature_map_sizes, anchor_sizes, anchor_ratios)
# for inference , the batch size is 1, the model output shape is [1, N, 4],
# so we expand dim for anchors to [1, anchor_num, 4]
anchors_exp = np.expand_dims(anchors, axis=0)
id2class = {0: 'Mask', 1: 'NoMask'}
111
30 def inference(image, conf_thresh=0.5,
31 iou_thresh=0.4,
32 target_shape=(160, 160),
33 draw_result=True,
34 show_result=True
35 ):
*1 def意为定义一个函数,紧接着是函数名,括号内部为函数的参数,内部为函数的 具体功能实现代码
下一节说明了各个参数的含义
:param image:3D numpy图像数组
:param conf_thresh:分类概率的最小阈值。
:param iou_thresh:NMS的iou阈值
:param target_shape:模型输入大小。
:param draw_result:是否将边框添加到图像。
:param show_result:是否显示图像。
47 # image = np.copy(image)
48 output_info = []
49 height, width, _ = image.shape
50 image_resized = cv2.resize(image, target_shape)
51 image_np = image_resized / 255.0 # 归一化到0~1
52 image_exp = np.expand_dims(image_np, axis=0)
53 y_bboxes_output, y_cls_output = tf_inference(sess, graph, image_exp)
*1 注释的含义是numpy中的深复制(深拷贝)参考
对对象及其子对象都进行copy一份,对新生成的对象修改删除操作不会影响到原对象。
*2
*3 cv2,resize用于对图像进行尺度缩放,可以使用各种内插方法进行处理。函数使用参考image原图,target_shape输出图像大小(即模型输入大小)
*4进行归一化处理
*5np.expand_dims的作用是通过在指定位置插入新的轴来扩展数组形状(扩展一个张量的维度),函数格式如下:np.expand_dims(array, axis),axis意为轴轴含义参考
132 if __name__ == "__main__":
parser = argparse.ArgumentParser(description="Face Mask Detection")
parser.add_argument('--img-mode', type=int, default=1, help='set 1 to run on image, 0 to run on video.')
parser.add_argument('--img-path', type=str, help='path to your image.')
parser.add_argument('--video-path', type=str, default='0', help='path to your video, `0` means to use camera.')
# parser.add_argument('--hdf5', type=str, help='keras hdf5 file')
args = parser.parse_args()
if args.img_mode:
imgPath = args.img_path
img = cv2.imread(imgPath)
img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
inference(img, show_result=True, target_shape=(260, 260))
else:
video_path = args.video_path
if args.video_path == '0':
video_path = 0
run_on_video(video_path, '', conf_thresh=0.5)
149
add_argument:读入命令行参数,该调用有多个参数。
用法:
ArgumentParser.add_argument(name or flags…[, action][, nargs][, const][, default][, type][, choices][, required][, help][, metavar][, dest])
name or flags - 选项字符串的名字或者列表,例如 foo 或者 -f, --foo。
action - 命令行遇到参数时的动作,默认值是 store。
default - 不指定参数时的默认值。
type - 命令行参数应该被转换成的类型。
help - 参数的帮助信息,当指定为 argparse.SUPPRESS 时表示不显示该参数的帮助信息.
*1建立解析对象:parser = argparse.ArgumentParser()
*2把parser中设置的所有"add_argument"给返回到args子类实例当中, 那么parser中增加的属性内容都会在args实例中,使用即可:
args = parser.parse_args()
*3运行时命令行输入 python tenforflow_infer.py --img-path img/demo2.jpg其实就是把路径赋值给args.img_path
这个解析很详细
的