C#机器学习之判断日报是否合格
原文作者:心萊科技肖鑫
簡單來說機器學習的核心步驟在于“獲取學習數據;選擇機器算法;定型模型;評估模型,預測模型結果”,下面本人就以判斷日報內容是否合格為例為大家簡單的闡述一下C#的機器學習。
第一步:問題分析
根據需求可以得出我們的模型是以日報的內容做為學習的特征確定的,然后通過模型判斷將該目標對象預測為是否符合標準(合格與不合格),簡單來說就是一種分類場景(此場景結果屬于二元分類,不是A就是B),那么也就確定了核心算法為分類算法當然還有其它的分類算法有興趣的可以自己去了解一下在這里就不多做說明了。
第二步:環境準備
其他的代碼編譯運行的環境并沒有太多要求,你只需要引用C#機器學習的NuGet?包,名為Microsoft.ML具體的安裝步驟在此就不做詳細介紹了。
第三步:準備數據
這里會準備兩個數據集 一個定型模型的數據集(可以稱之為學習資料)wikipedia-detox-250-line-data.tsv數據實例部分展示如下(你的數據按照這種排列格式即可該該格式的定義取決于你的輸入數據集類的結構在下面會講到):
SentimentSentimentText
1??第一天上班 無事
1?完成了領導的安排任務 ??
1?編寫了一些代碼然后寫了一些雜七雜八的文檔 ???
1??和一般的碼農做了一樣的事情
1?和產品經理一起做了一些項目上的事情 ?
1?早上來的時候就開始討論需求,然后開始寫代碼,快下班的時候完成了整個過程的文檔分享
0?***項目的整體編排會議,設計圖的首頁以及我的個人中心制作 ??
0?**項目需求的對接,需求的梳理,實體結構的定義,數據庫的遷移,腦圖的完善
0???1、**項目的模板消息代碼編寫,2、**項目管理后臺的模板發送完善,
定型模型數據集準備好之后還有一個評估模型的測試數據集(可以稱之為標準答案)wikipedia-detox-250-line-test.tsv格式與上面展示的評估數據集一樣
定型數據的數據越豐富算法的回歸曲線方程就會越接近理想的模型方程,你的模型預測結果就會越符合你的要求。
第四步:定義特征類
根據分享的模型確定其分析的特征項并定義為相關的類并且需要引用機器學習的包using?Microsoft.ML.Data;,由此模型定義的數據集類如下(結果可看注釋):
?///?<summary>
????///?輸入數據集類
????///?</summary>
????public?class?SentimentData
????{
????????///?<summary>
????????///?日志是否合格的值(0:為合格,1:不合格)
????????///?</summary>
????????[Column(ordinal:"0", name:"Label")]
????????public?float?Sentiment;
?
????????///?<summary>
????????///?日報內容
????????///?</summary>
????????[Column(ordinal:"1")]
????????public?string?SentimentText;
????}
?
????///?<summary>
????///?預測結果集類
????///?</summary>
????public?class?SentimentPrediction
????{
????????///?<summary>
????????///?預測值(是否合格)
????????///?</summary>
????????[ColumnName("PredictedLabel")]
????????public?bool?Prediction {get;set; }
?
????????///?<summary>
????????///?或然率(結果分布概率)
????????///?</summary>
????????[ColumnName("Probability")]
????????public?float?Probability {get;set; }
?
????}
第一個SentimentData類為輸入數據集類,指的就是根據定型的數據集的特征項定義的集類,第二個SentimentPrediction類為預測結果集類,也就是你所需要的結果的類定義 該類的結構一般受你所使用的學習算法影響,根據你的學習管道輸出的結果以及個人需求的綜合考慮來定義。輸入集類帶的Column屬性標注其在數據集的格式位置的編排以及何為Label值。預測集的PredictedLabel在預測和評估過程中使用。
第五步:代碼實現
首先定義以指定這些路徑和?_textLoader?變量,用來讀取數據或者是保存實驗數據,具體如下所示:
_trainDataPath?具有用于定型模型的數據集路徑。
_testDataPath?具有用于評估模型的數據集路徑。
_modelPath?具有在其中保存定型模型的路徑。
_textLoader?是用于加載和轉換數據集的?TextLoader。
?
?
然后定義程序的入口(main函數)以及相應的處理方法:
定義SaveModelAsFile方法將模型保存為 .zip 文件代碼如下所示:
?
????????private?static?void?SaveModelAsFile(MLContext mlContext, ITransformer model)
????????{
????????????using?(var?fs =new?FileStream(_modelPath, FileMode.Create, FileAccess.Write, FileShare.Write))
????????????????mlContext.Model.Save(model, fs);
?
????????????Console.WriteLine("模型保存路徑為{0}", _modelPath);
????????????Console.ReadLine();
????????}
定義Train方法選擇學習方法并且創建相應的學習管道,輸出定型后的模型model代碼如下所示:
?public?static?ITransformer Train(MLContext mlContext,string?dataPath)
????????{
????????????IDataView dataView = _textLoader.Read(dataPath);
?
????????????//數據特征化(按照管道所需的格式轉換數據)
????????????var?pipeline = mlContext.Transforms.Text.FeaturizeText(inputColumnName:"SentimentText", outputColumnName:"Features")
????????????//根據學習算法添加學習管道
????????????????.Append(mlContext.BinaryClassification.Trainers.FastTree(numLeaves: 50, numTrees: 50, minDatapointsInLeaves: 20));
????????????//得到模型
????????????var?model = pipeline.Fit(dataView);
????????????Console.WriteLine();
???????????//返回定型模型
????????????return?model;
????????}
模型定型之后,我們需要創建一個方法(Evaluate)來評測該模型的質量,根據你自己的標準測試數據集與該模型的符合程度來判斷,并且輸出相應的指標,該指標參數根據你所調用的評估方法返回具體的根據你的算法方程返回相應的方程的參數 。代碼如下所示:
?public?static?void?Evaluate(MLContext mlContext, ITransformer model)
????????{
????????????var?dataView = _textLoader.Read(_testDataPath);
????????????Console.WriteLine("===============用測試數據評估模型的準確性===============");
????????????var?predictions = model.Transform(dataView);
??????????//評測定型模型的質量
????????????var?metrics = mlContext.BinaryClassification.Evaluate(predictions,"Label");
????????????Console.WriteLine();
????????????Console.WriteLine("模型質量量度評估");
????????????Console.WriteLine("--------------------------------");
????????????Console.WriteLine($"精度:{metrics.Accuracy:P2}");
????????????Console.WriteLine($"Auc:{metrics.Auc:P2}");
????????????Console.WriteLine("=============== 模型結束評價 ===============");
????????????Console.ReadLine();
//評測完成之后開始保存定型的模型
????????????SaveModelAsFile(mlContext, model);
????????}
定義單個數據的預測方法(Predict)與批處理預測的方法(PredictWithModelLoadedFromFile):
單個數據集的預測代碼如下所示:
?private?static?void?Predict(MLContext mlContext, ITransformer model)
????????{
?//創建包裝器
????????????var?predictionFunction = model.CreatePredictionEngine<SentimentData, SentimentPrediction>(mlContext);
?
????????????SentimentData sampleStatement =new?SentimentData
????????????{
????????????????SentimentText ="愛車新需求開發;麥扣日志監控部分頁面數據綁定;"
????????????};
//預測結果
????????????var?resultprediction = predictionFunction.Predict(sampleStatement);
?
????????????Console.WriteLine();
????????????Console.WriteLine("===============單個測試數據預測 ===============");
?
????????????Console.WriteLine();
????????????Console.WriteLine($"日報內容:{sampleStatement.SentimentText}?| 是否合格:{(Convert.ToBoolean(resultprediction.Prediction) ?"合格"?:"不合格")}?| 符合率:{resultprediction.Probability}?");
????????????Console.WriteLine("=============== 預測結束 ===============");
????????????Console.WriteLine();
????????????Console.ReadLine();
????????}
批處理數據集預測方法代碼如下所示:
?public?static?void?PredictWithModelLoadedFromFile(MLContext mlContext)
????????{
????????????IEnumerable<SentimentData> sentiments =new[]
?????????????????????{
???????????????????????????new?SentimentData
??????????????????????{
?????????????????????SentimentText ="1、完成愛車年卡代碼編寫 2、與客戶完成需求對接"
??????????????????????},
????????????????????????????new?SentimentData
??????????????????????{
?????????????????????????SentimentText ="沒有工作內容"
??????????????????????}
?????????????????????};
?
????????????ITransformer loadedModel;
using?(var?stream =new?FileStream(_modelPath, FileMode.Open, FileAccess.Read, FileShare.Read))
????????????{
????????????????loadedModel = mlContext.Model.Load(stream);
????????????}
????????????//創建預測(也稱之為創建預測房屋)????????????
var?sentimentStreamingDataView = mlContext.Data.ReadFromEnumerable(sentiments);
????????????var?predictions = loadedModel.Transform(sentimentStreamingDataView);
????????????//使用模型預測結果值為1(不合格)還是0 ?(合格)??
???????var?predictedResults = mlContext.CreateEnumerable<SentimentPrediction>(predictions, reuseRowObject:false);
????????????Console.WriteLine();
?
????????????Console.WriteLine("=============== 多樣本加載模型的預測試驗 ===============");
?
????????????var?sentimentsAndPredictions = sentiments.Zip(predictedResults, (sentiment, prediction) => (sentiment, prediction));
?
????????????foreach?(var itemin?sentimentsAndPredictions)
????????????{
????????????????Console.WriteLine($"日報內容:{item.sentiment.SentimentText}?| 是否合格:{(Convert.ToBoolean(item.prediction.Prediction) ?"合格"?:"不合格")}?| 符合率:{item.prediction.Probability}?");
????????????}
????????????Console.WriteLine("=============== 預測結束 ===============");
????????????Console.ReadLine();
????????}
在以上的方法定義完成之后開始進行方法的調用:
public??static?void?Main(string[] args)
????????{
//創建一個MLContext,為ML作業提供一個上下文
????????????MLContext mlContext =new?MLContext(seed: 0);
//初始化_textLoader以將其重復應用于所需要的數據集
?????????_textLoader = mlContext.Data.CreateTextLoader(
????????columns:new?TextLoader.Column[]
????????{
????????new?TextLoader.Column("Label", DataKind.Bool,0),
????????new?TextLoader.Column("SentimentText", DataKind.Text,1)
????????},
?????????separatorChar:'\t',
?????????hasHeader:true
????????????);
?//定型模型
??????????var?model = Train(mlContext, _trainDataPath);
//評測模型
??????????Evaluate(mlContext, model);
//單個數據預測
??????????Predict(mlContext, model);
???????????//批處理預測數據
??????????PredictWithModelLoadedFromFile(mlContext);
?
????????}
準備代碼之后,你的小小的機器人就要開始學習啦,好吧開始編譯運行吧。。。。。。
運行產生結果為:?
由于訓練的數據集特征化參數的準確性以及數據的涵蓋廣度不夠導致定義的模型質量非常的不理想因此我們可以看到我們的預測結果也是不夠符合我們的理想狀態,可見我們小機器的學習之路是非常漫長的過程啊。
由此次的機器學習的小小實踐本人也深有體會,機器就像一個小孩一樣首先你得根據他的性格(特征化參數)確定應該給予他什么樣的學習環境(學習算法創建的學習管道)并提供學習資料(定型機器學習模型數據集),然后為其確定一個發展目標(評估模型數據集),并且不斷的進行考試(單個數據的預測與批量數據的預測),考試需要特定的考試場地(預測所需要調用的方法)。通過該種方式讓機器不斷的學習不斷的精進。
原文地址:https://www.cnblogs.com/codelove/p/10493970.html
.NET社區新聞,深度好文,歡迎訪問公眾號文章匯總 http://www.csharpkit.com
總結
以上是生活随笔為你收集整理的C#机器学习之判断日报是否合格的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 程序员过关斩将--你的面向接口编程一定对
- 下一篇: PuppeteerSharp: 更友好的