機器學習模型部署--打通前后端任督二脈

前言

學歷與定位

近日在某論壇,有網(wǎng)友提問道:搞機器學習是不是要博士或是碩士學歷搀玖,是不是要求很高余境,頂會論文?本科生或者更低學歷的灌诅,是不是就沒有機會了芳来?從最近公司的招聘來看,算法工程師的 bar 確實有在提高猜拾。但在某些事業(yè)部即舌,仍需要很大的人力來做落地場景。每個人都要找準自己的定位挎袜,公司也有它的部門定位顽聂。如果是發(fā)論文肥惭、要在學術界站穩(wěn)腳跟,給投資人“我們很重視最新技術”的信心紊搪,那博士確實很重要蜜葱。另一個角度,從實用角度來說耀石,研究生和本科生可能性價比更高牵囤。當然,作為一個小本就工作的人娶牌,沒有較為豐富的實戰(zhàn)經(jīng)驗奔浅,有機會的話,還是拿到碩士及更高學歷比較好诗良。這里的實戰(zhàn)經(jīng)驗就比如:搭建一個完整的汹桦、涉及算法模型、后端及前端的系統(tǒng)鉴裹。

mobile.jpg

模型算法的實用主義

機器學習的實用主義舞骆,不是在論文多少,而是用正確的方法去解決正確的問題径荔。而作為背后的工程師督禽,除了調(diào)參、除了寫 sql总处,做調(diào)包俠狈惫、做 sql boy、報表 boy 以外鹦马,在之前的文章也提到過胧谈,要學會做正確的展示,做全套的工程化實施荸频。畢竟菱肖,等排期很難受;有些情況前后端資源不夠旭从,或者優(yōu)先級很低稳强,那就需要自己動手了。以下以上面的垃圾郵件分類為例子和悦,說明該如何搭建一個前后端完整的機器學習系統(tǒng)退疫。

關注微信公眾號:谷粒先生,下載權重文件并第一時間獲取更新鸽素。

這里將本次的任務拆解蹄咖,分為三個部分來講。后端 flask付鹿、前端 Vue澜汤、ML 模型采用 flair,項目地址 kuhung/flask_vue_ML

后端 flask

相關依賴的安裝

pip install -r requirements.txt

核心函數(shù)

  1. 導入函數(shù)包
from flask import Flask, jsonify, request
from flask_cors import CORS # 做跨域的準備
from flask import session # 追蹤客戶端會話

from flair.models import TextClassifier # 模型導入舵匾,采用前不久開源的 flair 做文本分類
from flair.data import Sentence

  1. 準備工作
app = Flask(__name__) # 聲明準備
app.secret_key = "super_secret_key"

CORS(app)
classifier = TextClassifier.load_from_file('models/best-model.pt') # 模型加載

  1. 配置 flask 的路由
# 根路由配置
@app.route('/', methods=['GET'])
def index():
    return jsonify("welcome to Kuhung API")

# GET 方法俊抵,這里 session 的作用是追蹤客戶端會話,防止重復請求模型
@app.route('/api/tasks', methods=['GET'])
def get_result():
    result = []
    try:
        data_result = session['my_result']
        result.append ({'title': data_result['title'], 'tag': data_result['tag'] })
    except:
        result.append ({'title': 'The txt you input', 'tag': 'spam or ham' })
    return jsonify(result)

# POST 方法
@app.route('/api/task', methods=['POST'])
def input_predict_text():

    title = request.get_json()['title'] # 解析請求

    sentence = Sentence(title) # 對請求做數(shù)據(jù)預處理
    classifier.predict(sentence) # 調(diào)用模型坐梯,做預測徽诲,返回帶標簽的數(shù)據(jù)

    text = sentence.to_plain_string() # 解析出原始數(shù)據(jù)
    label = sentence.labels[0] # 解析出標簽
    result = {'title' : text, 'tag' : label.value} # 拼接成字典格式
    session['my_result'] = result # 存入 session ,以減少重復請求對模型的壓力
    
    return jsonify(result) # 返回 json 格式的數(shù)據(jù)

if __name__ == '__main__':
    app.run(debug=True)  # 開發(fā)過程中開啟 debug 調(diào)試模式

啟動服務

python app.py

前端 vue

前端采用 Vue 框架吵血,與后端分離谎替。使用 Webpack 進行資源管理與打包。

相關依賴的安裝

npm install -g vue-cli
npm install

自定義組件

通過 vue init webpack flask_vue_ML 后蹋辅,進入項目文件夾钱贯,增加自定義內(nèi)容。

index.html


<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <title>exposemodel</title>
  </head>
  <body>
    <div id="app"></div>
    <!-- 其它文件會自動注入這里 -->
  </body>
</html>

src 文件夾

  • components
    • Home.vue // 自定義組件侦另,增加
  • router
    • index.js // 路由秩命,修改
  • App.vue // 主組件,修改
  • main.js // 入口文件褒傅,修改
Home.vue

這里定義頁面的基本樣式弃锐,以及獲取數(shù)據(jù)的邏輯。

<template>
  <div id="todo-list-example" class="container">
    <!-- 我是進度條殿托,最上方的 -->
    <vue-progress-bar></vue-progress-bar>
    <div class="row">
      <div class="col-md-6 mx-auto">
        <h1 class="text-center">Natural Language Processing (NLP)</h1>
        <form v-on:submit.prevent="addNewTask">
          <label for="tasknameinput">Spam Classification</label>
          <input v-model="taskname" type="text" id="tasknameinput" class="form-control" placeholder="Enter Sentence">
          <button type="submit" class="btn btn-success btn-block mt-3">
            Submit
          </button>
        </form>
          
<!-- 省略表格定義內(nèi)容 -->


<script>
// 這里解決跨域請求問題霹菊,向后端發(fā)起請求
import axios from 'axios'

export default {
  data () {
    return {
      textClassify: [],
      id: '',
      taskname: '',
      isEdit: false
    }
  },
  mounted () {
    this.getTasks()
  },
    
// 省略進度條內(nèi)容
    
// 請求任務相關操作
    getTasks () {
      axios({ method: 'GET', url: '/api/tasks' }).then(
        result => {
          console.log(result.data)
          this.textClassify = result.data
        },
        error => {
          console.error(error)
        }
      )
    },
</script>
?```
index.js

定義路由,設定訪問路徑支竹,并將路徑和組件關聯(lián)

import Vue from 'vue'
import Router from 'vue-router'
import Home from '@/components/Home'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/',
      name: 'Home',
      component: Home
    }
  ]
})
App.vue

主組件

<template>
  <div id="app">
    <router-view/>
    <!-- 植入一波廣告:微信搜索:谷粒先生旋廷,關注我的公眾號 -->
    <img src="./assets/wechat.jpg">
  </div>
</template>

<script>
export default {
  name: 'App'
}
</script>

<style>
#app {
  font-family: 'Avenir', Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-align: center;
  color: #2c3e50;
  margin-top: 60px;
}
</style>
main.js

初始化實例并加載必要插件

// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
import Vue from 'vue'
import App from './App'
import router from './router'
import VueProgressBar from 'vue-progressbar'
require('../node_modules/bootstrap/dist/css/bootstrap.css')

Vue.config.productionTip = false

// 這是進度條
Vue.use(VueProgressBar, {
  color: 'rgb(143, 255, 199)',
  failedColor: 'red',
  height: '10px'
})

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  components: { App },
  template: '<App/>'
})

啟動服務

npm run dev

模型 flair

模型這里采用 fair 框架,該框架在 2018 年底發(fā)布唾戚,易用性和效果都較前方案有了較大提升柳洋。這里直接采用官方樣例訓練好的垃圾郵件分類模型的權重,也就是在上文后端所讀取的文件叹坦。關注我的公眾號:谷粒先生熊镣,回復權重,即可獲得權重文件??鏈接募书。

模型調(diào)用


from flair.models import TextClassifier # 模型導入绪囱,采用前不久開源的 flair 做文本分類
from flair.data import Sentence

classifier = TextClassifier.load_from_file('models/best-model.pt') # 模型加載

sentence = Sentence(title) # 對請求做數(shù)據(jù)預處理
classifier.predict(sentence) # 調(diào)用模型,做預測莹捡,返回帶標簽的數(shù)據(jù)

效果展示

本教程針對文本分類這個場景鬼吵,構建了一套前后端分離的“完整”框架,能夠給到一個最直觀的感受篮赢。當然齿椅,這里還有很多優(yōu)化空間琉挖,還有后續(xù)部署等事宜沒有詳細展開,有心的同學可以自行檢索學習涣脚。通過這套流程示辈,可以在測試服搭建一套實用主義哲學的算法模型。給到領導做展示或是公司內(nèi)部使用遣蚀,已經(jīng)足夠矾麻。項目地址 kuhung/flask_vue_ML

終端端網(wǎng)站訪問

flask_vue_ml.jpg

關注微信公眾號:谷粒先生,下載權重文件并第一時間獲取更新芭梯。

喜歡我的朋友险耀,別忘了點贊 ??、喜歡 ? +關注 ??哦玖喘,你的鼓勵是對我最大的支持~??

?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末甩牺,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子芒涡,更是在濱河造成了極大的恐慌柴灯,老刑警劉巖,帶你破解...
    沈念sama閱讀 211,561評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件费尽,死亡現(xiàn)場離奇詭異赠群,居然都是意外死亡,警方通過查閱死者的電腦和手機旱幼,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,218評論 3 385
  • 文/潘曉璐 我一進店門查描,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人柏卤,你說我怎么就攤上這事冬三。” “怎么了缘缚?”我有些...
    開封第一講書人閱讀 157,162評論 0 348
  • 文/不壞的土叔 我叫張陵勾笆,是天一觀的道長。 經(jīng)常有香客問我桥滨,道長窝爪,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,470評論 1 283
  • 正文 為了忘掉前任齐媒,我火速辦了婚禮蒲每,結果婚禮上,老公的妹妹穿的比我還像新娘喻括。我一直安慰自己邀杏,他們只是感情好,可當我...
    茶點故事閱讀 65,550評論 6 385
  • 文/花漫 我一把揭開白布唬血。 她就那樣靜靜地躺著望蜡,像睡著了一般唤崭。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上泣特,一...
    開封第一講書人閱讀 49,806評論 1 290
  • 那天浩姥,我揣著相機與錄音,去河邊找鬼状您。 笑死,一個胖子當著我的面吹牛兜挨,可吹牛的內(nèi)容都是我干的膏孟。 我是一名探鬼主播,決...
    沈念sama閱讀 38,951評論 3 407
  • 文/蒼蘭香墨 我猛地睜開眼拌汇,長吁一口氣:“原來是場噩夢啊……” “哼柒桑!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起噪舀,我...
    開封第一講書人閱讀 37,712評論 0 266
  • 序言:老撾萬榮一對情侶失蹤魁淳,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后与倡,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體界逛,經(jīng)...
    沈念sama閱讀 44,166評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,510評論 2 327
  • 正文 我和宋清朗相戀三年纺座,在試婚紗的時候發(fā)現(xiàn)自己被綠了息拜。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,643評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡净响,死狀恐怖少欺,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情馋贤,我是刑警寧澤赞别,帶...
    沈念sama閱讀 34,306評論 4 330
  • 正文 年R本政府宣布,位于F島的核電站配乓,受9級特大地震影響仿滔,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜扰付,卻給世界環(huán)境...
    茶點故事閱讀 39,930評論 3 313
  • 文/蒙蒙 一堤撵、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧羽莺,春花似錦实昨、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,745評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽丈挟。三九已至,卻和暖如春志电,著一層夾襖步出監(jiān)牢的瞬間曙咽,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,983評論 1 266
  • 我被黑心中介騙來泰國打工挑辆, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留例朱,地道東北人。 一個月前我還...
    沈念sama閱讀 46,351評論 2 360
  • 正文 我出身青樓鱼蝉,卻偏偏與公主長得像洒嗤,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子魁亦,可洞房花燭夜當晚...
    茶點故事閱讀 43,509評論 2 348

推薦閱讀更多精彩內(nèi)容

  • 基于Vue的一些資料 內(nèi)容 UI組件 開發(fā)框架 實用庫 服務端 輔助工具 應用實例 Demo示例 element★...
    嘗了又嘗閱讀 1,142評論 0 1
  • 簡說Vue (組件庫) https://github.com/ElemeFE/element" 餓了么出品的VUE...
    Estrus丶閱讀 1,584評論 0 1
  • UI組件 element- 餓了么出品的Vue2的web UI工具套件 Vux- 基于Vue和WeUI的組件庫 m...
    35eeabfa0772閱讀 3,264評論 7 12
  • UI組件 element - 餓了么出品的Vue2的web UI工具套件 Vux - 基于Vue和WeUI的組...
    魯大師666閱讀 43,369評論 5 97
  • 解題思路 : 從 root 開始把所有節(jié)點用 BFS 方式放入 vector ( 節(jié)點只要不是 nullptr 就...
    一枚煎餅閱讀 178評論 0 0