新增三倍的图片

文件布局如下:

 ~/sandy/image下有几个文件夹,它们分别装着每一类的图片。

问题:要把图片增加三倍。

扩增数据来提升模型性能。换言之,数据扩增对于训练深度网络来说是必须的。 常用的方法:

1. 沿着x轴将图片左右翻转

2. 随机的剪切(可以是指定的尺寸,固定的步长)、缩放、旋转

3. 颜色抖动(RGB值,在一定的范围内进行随机的增减)

4. 提高图像中像素的饱和度和值(即 HSV 颜色空间的 S 和 V 成分)到 0.250.25 和 44 之间(在一个样本图像内要保证各个像素该值是一样的),再在图像上加上一个范围在 [−0.1,0.1][−0.1,0.1] 之间的值给 H ( hue ,即 HSV 中的色调)这个成分。

5. 用pca来改变RGB的强度值,产生分别对应的特征值和特征向量,然后用均值为0方差为0.1的随机数与特征值和特征向量相乘得到新的数据。(《ImageNet Classification with Deep Convolutional Neural Networks》

解:

用了前三种方法。在终端执行命令 sh getFileRun.sh 就可以解了。

效果是:

  /home/dog/sandy/image_doc/1 第一个文件(apple)用这三种方法产生的文件。

  /home/dog/sandy/image_doc/2 第二个文件(banana)用这三种方法产生的文件

  /home/dog/sandy/image_doc/3 第三个文件(strawberry)用这三种方法产生的文件

  ---

  /home/dog/sandy/image_labels存的是对image下的每一类图像的路径。比如image下有一个文件夹是apple,里面全是apple图片,那么在/home/dog/sandy/image_labels下就会有一个apple.txt,这个txt里都是apple文件夹下的图片的路径。

  /home/dog/sandy/image_label_txt下存的是一个all.txt,这个txt的内容就类似于:/home/dog/sandy/image_labels/image_1.txt---》总的txt的汇总。

原始代码如下:

--------------------------------------运行的shell文件----------------------------------------

getFileRun.sh的内容:

echo "Starting..."
echo
echo "Stabilizing image path..."

sh pre_processing.sh ~/sandy/image ~/sandy/image_labels ~/sandy/image_label_txt
echo
echo "Create image"

mkdir -p image_doc

g++ class10.cpp -o class10 `pkg-config opencv --cflags --libs`

echo
./class10 ~/sandy/image_label_txt/all.txt

echo "All are finishen"

--------------------------------------------------预处理shell-------------------------------------

pre_processing.sh的内容:

dataset_path=$1
path_to_label_list=$2
label=$3

mkdir -p $path_to_label_list
mkdir -p $label

cd $dataset_path;

for f in *;
do for g in $f/*;
do echo $dataset_path/$g;
done > $path_to_label_list/$f.txt ;
done

echo "The label file is done!";

cd ..

cd $path_to_label_list;
for f in *;
do echo $path_to_label_list/$f;
done > $label/all.txt;


echo "All finished!";

-------------------------------------主文件---------------------------------------

class10.cpp的内容如下。

#include <iostream>
#include <cstring>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <fstream>
#include <time.h>

#include <opencv2/opencv.hpp>

using namespace cv;
using namespace std;

void build_dir(string &dir);
void flipImg(Mat& src, unsigned int image_class,unsigned int image_number);
void average(const Mat &img, Point_<int> a, Point_<int> b, Vec3b &p);
void cropImg(const Mat &src, double xRatio, double yRatio, unsigned int image_class,unsigned int image_number);
void rgbChange(Mat& src,unsigned int image_class,unsigned int image_number);
//void fileSave(unsigned int image_class, Mat& dst, unsigned int image_number);
void fileSave(unsigned int image_class, string str, Mat& dst, unsigned int image_number);

int main(int argc,char* argv[])
{
char *path_to_image_list = argv[1];//这里给它传个总的label.txt ~/sandy/image_labels
FILE *fp_txt = fopen(path_to_image_list, "r");//指向的是每一类的txt


//为每一类建一个目录来存放
unsigned int image_class=1;
while(!feof(fp_txt))//all.txt下的内容:
{
char image_txt[300];
//fscanf(fp_txt, "%s", image_txt);//image_txt=/home/dog/sandy/image_labels/image_1.txt

if(fscanf(fp_txt, "%s", image_txt)<=0)//防止重读最后一行

  break;
printf("%s\n", image_txt);
FILE *fp_image = fopen(image_txt,"r");//指向一个个jpg路劲
char image_name[300];
unsigned int image_number= 0;//这样的话,每类文件(图片)都是从1开始标记
//为每一类建一个目录来存放
//unsigned int image_class=1;
//-----cancel
string dir;
char s[40];
sprintf(s,"%s/%d","./image_doc",image_class);
dir = s;
//-----cancel
build_dir(dir);

cout<<"dir===="<<dir<<endl;
while(!feof(fp_image))
{
if(fscanf(fp_image, "%s", image_name)<=0)

  break;
++image_number;//
Mat src = imread(image_name);


RNG rng;
double xRatio=rng.uniform(0.9,0.99);
double yRatio=rng.uniform(0.9,0.99);

//char * f_path="./new_image_";
flipImg( src,image_class, image_number);
cropImg(src, xRatio, yRatio,image_class,image_number);
rgbChange(src,image_class,image_number);
}
fclose(fp_image);
++image_class;//
cout<<"finished: "<<image_class<<endl;
}
fclose(fp_txt);

return 0;
}

void build_dir(string &dir)
{
//string dir="./image_doc";
//string dir="./new_image";
if (access(dir.c_str(), 0) == -1)
{
cout<<dir<<" is not existing"<<endl;
cout<<"now make it"<<endl;
int flag=mkdir(dir.c_str(), 0777);
if (flag == 0)
cout<<"make successfully"<<endl;
else
cout<<"make errorly"<<endl;
}
else
cout<<dir<<" is existing"<<endl;
cout<<"end..."<<endl;
}
//---
void flipImg(Mat& src, unsigned int image_class,unsigned int image_number)
{
Mat dst;
flip(src, dst, 1); // flip by x axis
//
string str = "flip";
fileSave(image_class,str,dst,image_number);
}
//---
void average(const Mat &img, Point_<int> a, Point_<int> b, Vec3b &p)
{

const Vec3b *pix;
Vec3i temp;
for (int i = a.x; i <= b.x; i++){
pix = img.ptr<Vec3b>(i);
for (int j = a.y; j <= b.y; j++){
temp[0] += pix[j][0];
temp[1] += pix[j][1];
temp[2] += pix[j][2];
}
}

int count = (b.x - a.x + 1) * (b.y - a.y + 1);
p[0] = temp[0] / count;
p[1] = temp[1] / count;
p[2] = temp[2] / count;
}

void cropImg(const Mat &src, double xRatio, double yRatio, unsigned int image_class,unsigned int image_number)
{
Mat dst;
int rows = static_cast<int>(src.rows * xRatio);
int cols = static_cast<int>(src.cols * yRatio);

dst.create(rows, cols, src.type());

int lastRow = 0;
int lastCol = 0;

Vec3b *p;
for (int i = 0; i < rows; i++) {
p = dst.ptr<Vec3b>(i);
int row = static_cast<int>((i + 1) / xRatio + 0.5) - 1;

for (int j = 0; j < cols; j++) {
int col = static_cast<int>((j + 1) / yRatio + 0.5) - 1;

Vec3b pix;
average(src, Point_<int>(lastRow, lastCol), Point_<int>(row, col), pix);
p[j] = pix;

lastCol = col + 1; //下一个子块左上角的列坐标,行坐标不变
}
lastCol = 0; //子块的左上角列坐标,从0开始
lastRow = row + 1; //子块的左上角行坐标
}
string str = "crop";
fileSave(image_class,str,dst,image_number);
}
//---
void rgbChange(Mat& src,unsigned int image_class,unsigned int image_number)
{
//产生随机值,进行颜色抖动
RNG rng;
double div=rng.uniform(0.0,0.9);
//随机对R.G.B进行抖动
srand((unsigned)time(NULL));
unsigned int channel_ =rand() % 3 +1;

Mat dst;
src.copyTo(dst);//不改变源图像

// get iterators
Mat_<Vec3b>::iterator it= dst.begin<Vec3b>();
Mat_<Vec3b>::iterator itend= dst.end<Vec3b>();

for ( ; it!= itend; ++it)
{
(*it)[channel_]= (*it)[channel_]/div*div + div/2;

}
cout<<"channel_="<<channel_<<endl;
cout<<"div="<<div<<endl;
string str = "rgb";
fileSave(image_class,str,dst,image_number);
}
//---
void fileSave(unsigned int image_class, string str, Mat& dst, unsigned int image_number)
{
/*
//创建存放的目录
if (access(file_name.c_str(), 0) == -1)
{
cout<<file_name<<" is not existing"<<endl;
cout<<"now making it"<<endl;
int flag=mkdir(file_name.c_str(), 0777);
if (flag == 0)
cout<<"make successfully"<<endl;
else
cout<<"make errorly"<<endl;
}
else
cout<<file_name<<" is existing"<<endl;
cout<<"end..."<<endl;
*/

char image_save[300];//保存文件名

sprintf(image_save,"%s/%d/%s_%d%s","./image_doc",image_class,str.c_str(),image_number,".jpg");

string img_name = image_save;

imwrite(img_name, dst);

//imwrite(image_save, dst);
//imshow(str, dst);
//waitKey(0);
}

 

posted on 2017-04-20 21:18  北海盗  阅读(262)  评论(0编辑  收藏  举报