欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

机器学习框架ML.NET学习笔记【7】人物图片颜值判断

程序员文章站 2022-03-20 08:00:47
一、概述 这次要解决的问题是输入一张照片,输出人物的颜值数据。 学习样本来源于华南理工大学发布的SCUT-FBP5500数据集,数据集包括 5500 人,每人按颜值魅力打分,分值在 1 到 5 分之间。其中包括男性、女性、中国人、外国人四个分类。 SCUT-FBP5500_full.csv文件标记了 ......

一、概述

 这次要解决的问题是输入一张照片,输出人物的颜值数据。

学习样本来源于华南理工大学发布的scut-fbp5500数据集,数据集包括 5500 人,每人按颜值魅力打分,分值在 1 到 5 分之间。其中包括男性、女性、中国人、外国人四个分类。

机器学习框架ML.NET学习笔记【7】人物图片颜值判断

 

scut-fbp5500_full.csv文件标记了每个图片人物的颜值打分数据。(我把分值一项乘以了20,变成了满分100分,不影响计算结果)

整个程序处理流程和前一篇图片分类的基本一致,唯一的区别,分类用的是多元分类算法,这次采用的是回归算法。

 

二、源码

 下面是全部代码:

namespace tensorflow_imageclassification
{    

    class program
    {
        //assets files download from:https://gitee.com/seabluescn/ml_assets
        static readonly string assetsfolder = @"d:\stepbystep\blogs\ml_assets";
        static readonly string traindatafolder = path.combine(assetsfolder, "facevaluedetection", "scut-fbp5500");
        static readonly string traintagspath = path.combine(assetsfolder, "facevaluedetection", "scut-fbp5500_asia_full.csv");
        static readonly string testdatafolder = path.combine(assetsfolder, "facevaluedetection", "testimages");
        static readonly string inceptionpb = path.combine(assetsfolder, "tensorflow", "tensorflow_inception_graph.pb");
        static readonly string imageclassifierzip = path.combine(environment.currentdirectory, "mlmodel", "imageclassifier.zip");

        //配置用常量
        private struct imagenetsettings
        {
            public const int imageheight = 224;
            public const int imagewidth = 224;
            public const float mean = 117;
            public const float scale = 1;
            public const bool channelslast = true;
        }

        static void main(string[] args)
        {
            trainandsavemodel();
            loadandprediction();

            console.writeline("hit any key to finish the app");
            console.readkey();
        }

        public static void trainandsavemodel()
        {
            mlcontext mlcontext = new mlcontext(seed: 1);

            // step 1: 准备数据
            var fulldata = mlcontext.data.loadfromtextfile<imagenetdata>(path: traintagspath, separatorchar: ',', hasheader: true);
            var traintestdata = mlcontext.data.traintestsplit(fulldata, testfraction: 0.2);
            var traindata = traintestdata.trainset;
            var testdata = traintestdata.testset;

            // step 2:创建学习管道
            var pipeline = mlcontext.transforms.loadimages(outputcolumnname: "input", imagefolder: traindatafolder, inputcolumnname: nameof(imagenetdata.imagepath))
                .append(mlcontext.transforms.resizeimages(outputcolumnname: "input", imagewidth: imagenetsettings.imagewidth, imageheight: imagenetsettings.imageheight, inputcolumnname: "input"))
                .append(mlcontext.transforms.extractpixels(outputcolumnname: "input", interleavepixelcolors: imagenetsettings.channelslast, offsetimage: imagenetsettings.mean))
                .append(mlcontext.model.loadtensorflowmodel(inceptionpb).
                     scoretensorflowmodel(outputcolumnnames: new[] { "softmax2_pre_activation" }, inputcolumnnames: new[] { "input" }, addbatchdimensioninput: true))
                .append(mlcontext.regression.trainers.lbfgspoissonregression(labelcolumnname: "label", featurecolumnname: "softmax2_pre_activation"));


            // step 3:通过训练数据调整模型             
            itransformer model = pipeline.fit(traindata);          

            // step 4:评估模型           
            var predictions = model.transform(testdata); 
            var metrics = mlcontext.regression.evaluate(predictions, labelcolumnname: "label", scorecolumnname: "score");
            printregressionmetrics( metrics);          

            //step 5:保存模型
            console.writeline("====== save model to local file =========");
            mlcontext.model.save(model, traindata.schema, imageclassifierzip);
        }

        static void loadandprediction()
        {
            mlcontext mlcontext = new mlcontext(seed: 1);

            // load the model
            itransformer loadedmodel = mlcontext.model.load(imageclassifierzip, out var modelinputschema);

            // make prediction function (input = imagenetdata, output = imagenetprediction)
            var predictor = mlcontext.model.createpredictionengine<imagenetdata, imagenetprediction>(loadedmodel);
            
            directoryinfo testdir = new directoryinfo(testdatafolder);
            foreach (var jpgfile in testdir.getfiles("*.jpg"))
            {
                imagenetdata image = new imagenetdata();
                image.imagepath = jpgfile.fullname;
                var pred = predictor.predict(image);

                console.writeline($"filename:{jpgfile.name}:\tpredict result:{pred.facevalue}");
            }
        }       
    }

    public class imagenetdata
    {
        [loadcolumn(0)]
        public string imagepath;

        [loadcolumn(1)]
        public float label;
    }

    public class imagenetprediction
    {
        [columnname("score")]
        public float facevalue;
    }   
}

  

三、分析

1、数据处理通道

// step 2:创建学习管道
var pipeline = mlcontext.transforms.loadimages(...)
    .append(mlcontext.transforms.resizeimages(...)
    .append(mlcontext.transforms.extractpixels(...)
    .append(mlcontext.model.loadtensorflowmodel(inceptionpb)
        .scoretensorflowmodel(outputcolumnnames: new[] { "softmax2_pre_activation" }, inputcolumnnames: new[] { "input" }, addbatchdimensioninput: true))    
.append(mlcontext.regression.trainers.lbfgspoissonregression(labelcolumnname: "label", featurecolumnname: "softmax2_pre_activation"));

 loadimages、resizeimages、extractpixels:上篇文章都已经介绍过了;

scoretensorflowmodel方法把图片像素值转换为图片特征数据,并存储在softmax2_pre_activation列,label列保存的是颜值数据,通过回归算法形成模型,当输入新的特征数据时就可以得出对应的颜值数据。

算法采用的是:l-bfgs poisson regression (拟牛顿法泊松回归)

 

2、预测结果

 在网上找了一些大头照,通过程序进行预测,右侧是预测结果:

 

机器学习框架ML.NET学习笔记【7】人物图片颜值判断

 

预测结果虽然和我认为的不完全一致,但总体上可以接受,大方向没什么问题,存在偏差主要有以下几个因素:

1、学习样本的客观性存疑,其打分数据可能是分配给多人打分后汇总的,每个人标准不一致;

2、被检测图片不是很规范,如尺寸、比例、背景、使用美颜软件等;

3、颜值本身就不具备客观性,不存在标准答案,如果我说林心如比如花漂亮,大家肯定都同意,但我如果说古力娜扎比迪丽热巴漂亮,肯定有人不赞成。

 

四、资源获取 

源码下载地址:https://github.com/seabluescn/study_ml.net

工程名称:tensorflow_facevaluedetection

资源获取:https://gitee.com/seabluescn/ml_assets (scut-fbp5500)

点击查看机器学习框架ml.net学习笔记系列文章目录