赞
踩
1.训练图片分类模型的三种方法
(1).从无到有,先确定好算法框架,准备好需要训练的数据集,从头开始训练,参数一开始也是初始化的随机值,一个批次一个批次地进行训练。
(2).准备好已经训练好的模型,权值参数也都已经确定,只训练最后一层,因为前面的参数都是经过大量图片的训练来的,所以参数都比较好,比如卷积层主要的作用的对图像特征的提取,我们要做自己的分类模型的话也得对图像进行特征提取,做特征提取的话直接使用训练好的权值也行。
(3).跟2差不多,不同的是都之前的参数也做微调。
2.retrain图片分类模型
(1). https://github.com/tensorflow/tensorflow 下载官方包 有一些官方提供的案例,里面有后面要用到的retrain.py文件。
(2).下载图片集
网址:http://www.robots.ox.ac.uk/~vgg/data/
(3)然后写批处理文件
:
- activate py3 ^
- python E:/graduate_student/deep_learning/tensorflow-master/tensorflow-master/tensorflow/examples/image_retraining/retrain.py ^
- --bottleneck_dir bottleneck ^
- --how_many_training_steps 200 ^
- --model_dir D:/software/mycodes/python35/py3/inception_model/ ^
- --output_graph output_graph.pb ^
- --output_labels output_labels.txt ^
- --image_dir imagedata/
- pause
bottleneck 瓶颈,图片预处理的时候把这个值算出来
output_graph 输出训练好的模型到当前文件夹
output_labels 输出训练好的标签到当前文件夹
image的格式需要里面文件夹的名字代表分类类型。(里面图片不能由大写字母也不能由中文!!)
运行批处理文件,得到:
(4)测试训练好的模型:
代码:
# coding: utf-8 # In[1]: import tensorflow as tf import os import numpy as np import re from PIL import Image import matplotlib.pyplot as plt # In[2]: lines = tf.gfile.GFile('E:/graduate_student/deep_learning/a-tensorflow/9/retain/output_labels.txt').readlines() uid_to_human = {} #一行一行读取数据 for uid,line in enumerate(lines) : #去掉换行符 line=line.strip('\n') uid_to_human[uid] = line def id_to_string(node_id): if node_id not in uid_to_human: return '' return uid_to_human[node_id] #创建一个图来存放google训练好的模型 with tf.gfile.FastGFile('E:/graduate_student/deep_learning/a-tensorflow/9/retain/output_graph.pb', 'rb') as f: graph_def = tf.GraphDef() graph_def.ParseFromString(f.read()) tf.import_graph_def(graph_def, name='') with tf.Session() as sess: softmax_tensor = sess.graph.get_tensor_by_name('final_result:0') #遍历目录 for root,dirs,files in os.walk('E:/graduate_student/deep_learning/a-tensorflow/9/retain/images/'): for file in files: #载入图片 image_data = tf.gfile.FastGFile(os.path.join(root,file), 'rb').read() predictions = sess.run(softmax_tensor,{'DecodeJpeg/contents:0': image_data})#图片格式是jpg格式 predictions = np.squeeze(predictions)#把结果转为1维数据 #打印图片路径及名称 image_path = os.path.join(root,file) print(image_path) #显示图片 img=Image.open(image_path) plt.imshow(img) plt.axis('off') plt.show() #排序 top_k = predictions.argsort()[::-1] print(top_k) for node_id in top_k: #获取分类名称 human_string = id_to_string(node_id) #获取该分类的置信度 score = predictions[node_id] print('%s (score = %.5f)' % (human_string, score)) print()
结果:
使用finetune的优点:1.训练速度快,计算量少,只计算最后一层。2.迭代周期少,因为训练的权值少。3.需要使用到图片的数据量比较少。
3.重头开始训练图片识别模型
(1)tensorflow官方包里下载:https://github.com/tensorflow/models
(2)准备好分类图片
(3)图像预处理,生成tfrecord文件。
程序:
# coding: utf-8 # In[2]: import tensorflow as tf import os import random import math import sys # In[3]: #验证集数量 _NUM_TEST = 500 #随机种子 _RANDOM_SEED = 0 #数据块 _NUM_SHARDS = 5 #数据集路径 DATASET_DIR = "E:/graduate_student/deep_learning/a-tensorflow\9/retain/imagedata/" #标签文件名字 LABELS_FILENAME = "E:/graduate_student/deep_learning/a-tensorflow/9/retain/labels.txt" #定义tfrecord文件的路径+名字 def _get_dataset_filename(dataset_dir, split_name, shard_id): output_filename = 'image_%s_%05d-of-%05d.tfrecord' % (split_name, shard_id, _NUM_SHARDS) return os.path.join(dataset_dir, output_filename) #判断tfrecord文件是否存在 def _dataset_exists(dataset_dir): for split_name in ['train', 'test']: for shard_id in range(_NUM_SHARDS): #定义tfrecord文件的路径+名字 output_filename = _get_dataset_filename(dataset_dir, split_name, shard_id) if not tf.gfile.Exists(output_filename): return False return True #获取所有文件以及分类 def _get_filenames_and_classes(dataset_dir): #数据目录 directories = [] #分类名称 class_names = [] for filename in os.listdir(dataset_dir): #合并文件路径 path = os.path.join(dataset_dir, filename) #判断该路径是否为目录 if os.path.isdir(path): #加入数据目录 directories.append(path) #加入类别名称 class_names.append(filename) photo_filenames = [] #循环每个分类的文件夹 for directory in directories: for filename in os.listdir(directory): path = os.path.join(directory, filename) #把图片加入图片列表 photo_filenames.append(path) return photo_filenames, class_names def int64_feature(values): if not isinstance(values, (tuple, list)): values = [values] return tf.train.Feature(int64_list=tf.train.Int64List(value=values)) def bytes_feature(values): return tf.train.Feature(bytes_list=tf.train.BytesList(value=[values])) def image_to_tfexample(image_data, image_format, class_id): #Abstract base class for protocol messages. return tf.train.Example(features=tf.train.Features(feature={ 'image/encoded': bytes_feature(image_data), 'image/format': bytes_feature(image_format), 'image/class/label': int64_feature(class_id), })) def write_label_file(labels_to_class_names, dataset_dir,filename=LABELS_FILENAME): labels_filename = os.path.join(dataset_dir, filename) with tf.gfile.Open(labels_filename, 'w') as f: for label in labels_to_class_names: class_name = labels_to_class_names[label] f.write('%d:%s\n' % (label, class_name)) #把数据转为TFRecord格式 def _convert_dataset(split_name, filenames, class_names_to_ids, dataset_dir): assert split_name in ['train', 'test'] #计算每个数据块有多少数据 num_per_shard = int(len(filenames) / _NUM_SHARDS) with tf.Graph().as_default(): with tf.Session() as sess: for shard_id in range(_NUM_SHARDS): #定义tfrecord文件的路径+名字 output_filename = _get_dataset_filename(dataset_dir, split_name, shard_id) with tf.python_io.TFRecordWriter(output_filename) as tfrecord_writer: #每一个数据块开始的位置 start_ndx = shard_id * num_per_shard #每一个数据块最后的位置 end_ndx = min((shard_id+1) * num_per_shard, len(filenames)) for i in range(start_ndx, end_ndx): try: sys.stdout.write('\r>> Converting image %d/%d shard %d' % (i+1, len(filenames), shard_id)) sys.stdout.flush() #读取图片 image_data = tf.gfile.FastGFile(filenames[i], 'r').read() #获得图片的类别名称 class_name = os.path.basename(os.path.dirname(filenames[i])) #找到类别名称对应的id class_id = class_names_to_ids[class_name] #生成tfrecord文件 example = image_to_tfexample(image_data, b'jpg', class_id) tfrecord_writer.write(example.SerializeToString()) except IOError as e: print("Could not read:",filenames[i]) print("Error:",e) print("Skip it\n") sys.stdout.write('\n') sys.stdout.flush() if __name__ == '__main__': #判断tfrecord文件是否存在 if _dataset_exists(DATASET_DIR): print('tfcecord文件已存在') else: #获得所有图片以及分类 photo_filenames, class_names = _get_filenames_and_classes(DATASET_DIR) #把分类转为字典格式,类似于{'house': 3, 'flower': 1, 'plane': 4, 'guitar': 2, 'animal': 0} class_names_to_ids = dict(zip(class_names, range(len(class_names)))) #把数据切分为训练集和测试集 random.seed(_RANDOM_SEED) random.shuffle(photo_filenames) training_filenames = photo_filenames[_NUM_TEST:] testing_filenames = photo_filenames[:_NUM_TEST] #数据转换 _convert_dataset('train', training_filenames, class_names_to_ids, DATASET_DIR) _convert_dataset('test', testing_filenames, class_names_to_ids, DATASET_DIR) #输出labels文件 labels_to_class_names = dict(zip(range(len(class_names)), class_names)) write_label_file(labels_to_class_names, DATASET_DIR)
得到:
和
(4)批处理文件:
1.在slim里面加入image文件夹,里面放入图片tfrecord文件
2.在slim文件夹里的datasets文件夹里新建
程序如下:
"""Provides data for the flowers dataset. The dataset scripts used to create the dataset can be found at: tensorflow/models/slim/datasets/download_and_convert_flowers.py """ from __future__ import absolute_import from __future__ import division from __future__ import print_function import os import tensorflow as tf from datasets import dataset_utils slim = tf.contrib.slim _FILE_PATTERN = 'image_%s_*.tfrecord' SPLITS_TO_SIZES = {'train': 1000, 'test': 500} _NUM_CLASSES = 5 _ITEMS_TO_DESCRIPTIONS = { 'image': 'A color image of varying size.', 'label': 'A single integer between 0 and 4', } def get_split(split_name, dataset_dir, file_pattern=None, reader=None): """Gets a dataset tuple with instructions for reading flowers. Args: split_name: A train/validation split name. dataset_dir: The base directory of the dataset sources. file_pattern: The file pattern to use when matching the dataset sources. It is assumed that the pattern contains a '%s' string so that the split name can be inserted. reader: The TensorFlow reader type. Returns: A `Dataset` namedtuple. Raises: ValueError: if `split_name` is not a valid train/validation split. """ if split_name not in SPLITS_TO_SIZES: raise ValueError('split name %s was not recognized.' % split_name) if not file_pattern: file_pattern = _FILE_PATTERN file_pattern = os.path.join(dataset_dir, file_pattern % split_name) # Allowing None in the signature so that dataset_factory can use the default. if reader is None: reader = tf.TFRecordReader keys_to_features = { 'image/encoded': tf.FixedLenFeature((), tf.string, default_value=''), 'image/format': tf.FixedLenFeature((), tf.string, default_value='png'), 'image/class/label': tf.FixedLenFeature( [], tf.int64, default_value=tf.zeros([], dtype=tf.int64)), } items_to_handlers = { 'image': slim.tfexample_decoder.Image(), 'label': slim.tfexample_decoder.Tensor('image/class/label'), } decoder = slim.tfexample_decoder.TFExampleDecoder( keys_to_features, items_to_handlers) labels_to_names = None if dataset_utils.has_labels(dataset_dir): labels_to_names = dataset_utils.read_label_file(dataset_dir) return slim.dataset.Dataset( data_sources=file_pattern, reader=reader, decoder=decoder, num_samples=SPLITS_TO_SIZES[split_name], items_to_descriptions=_ITEMS_TO_DESCRIPTIONS, num_classes=_NUM_CLASSES, labels_to_names=labels_to_names)
然后在datasets文件夹里的里修改:
添加myimages。
3.在slim目录下新建批处理文件。 其中,train_image_classifier.py是在(1)里下载的文件里的程序,在slim文件夹里面,slim文件夹需要拷贝到当前目录。
- D:\Anaconda2\envs\PY3\python E:/graduate_student/deep_learning/models-master/models-master/research/slim/train_image_classifier.py ^
- --train_dir=D:/software/mycodes/python3/python35/captcha/model/ ^
- --dataset_name=myimages ^
- --dataset_split_name=train ^
- --dataset_dir=D:/software/mycodes/python3/python35/captcha/image ^
- --batch_size=10 ^
- --max_number_of_steps=10000 ^
- --model_name=inception_v3 ^
- pause
然后运行批处理文件。缓慢运行。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。