使用go制作微服务数据计算
Posted qianbo_insist
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用go制作微服务数据计算相关的知识,希望对你有一定的参考价值。
目的
1 主进程为nodejs 进程,为了给nodejs 进程提供计算心率hrv服务,制作该微服务进程,占用一个端口
2 利用go服务携程进行概率计算服务,不占用nodejs主进程
2 图示结构
2.1步骤如下
a 从传感器传入数据,接收到数据以后存储
b 需要计算的时候调用算法服务
2.2 如下图所示
3 微服务制作
3.1 充分利用go语言携程功能,制作sdnn心率计算包
hrv 5 min RR 间期 平均值标准差 sdann
24h 正常的RR间期总体标准差 sdnn
24h 每5分钟时段 标准差的平均值 sdnn index
两个相邻RR间期 差值的均方根RMSSD
24h 相邻两个正常RR 间期差值 大于50ms 的个数百分比pnn50
主要计算公式如下
3.2 制作http服务示例
写好mode包模式,go.mode 内容如下
module hrv
go 1.15
require github.com/garyburd/redigo v1.6.3
制作数据结构
如下,心率数据和时间,姓名
type Data struct
Heart int
Time int
Name string
type Cmd struct
Type int
Data []Data
携程函数示例
func calculate1(cmd *Cmd, w http.ResponseWriter)
//in1 := []float3271, 72, 69, 70, 65, 74
size := len(cmd.Data)
var in []float32 = make([]float32, size)
for i, v := range cmd.Data
in[i] = (float32)(v.Heart)
//标准差函数在sdnn包里面
ret := sdnn.Get_Stddev(in)
fmt.Fprintf(w, "%f", ret)
//
启动函数的时候这样写
go calculate(cmd,w)
这样没接收到一个任务以后,都会启动携程处理,然后返回结果
package main
import (
"encoding/json"
"fmt"
"hrv/sdnn"
"html"
"io/ioutil"
"log"
"net/http"
)
type Data struct
Heart int
Time int
Name string
type Cmd struct
Type int
Data []Data
// 创建一个错误处理函数,避免过多的 if err != nil 出现
func dropErr(e error)
if e != nil
panic(e)
func calculate1(cmd *Cmd, w http.ResponseWriter)
//in1 := []float3271, 72, 69, 70, 65, 74
size := len(cmd.Data)
var in []float32 = make([]float32, size)
for i, v := range cmd.Data
in[i] = (float32)(v.Heart)
ret := sdnn.Get_Stddev(in)
fmt.Fprintf(w, "%f", ret)
//
func main()
runtime.GOMAXPROCS(4)
http.HandleFunc("/hrv", func(w http.ResponseWriter, r *http.Request)
fmt.Println(html.EscapeString(r.URL.Path))
if r.Method == "POST"
b, err := ioutil.ReadAll(r.Body)
if err != nil
log.Println("Read failed:", err)
defer r.Body.Close()
cmd := &Cmd
err = json.Unmarshal(b, cmd)
if err != nil
log.Println("json format error:", err)
//携程处理
go calculate1(cmd, w)
log.Println("cmd:", string(b))
log.Println("cmd:", cmd.Data[0])
//w.ResponseWriter("1")
else
log.Println("not support")
w.WriteHeader(405)
return
)
fmt.Println("server lister at 8080")
log.Fatal(http.ListenAndServe(":8080", nil))
为了充分利用多核,我们可以设定并发携程处理器个数
runtime.GOMAXPROCS(4)
测试client
package main
import (
"bytes"
"fmt"
"io/ioutil"
"net/http"
)
type Data struct
Heart int
Time int
Name string
type Cmd struct
Type int
Data []Data
func main()
str := `"Type":1,"Data":["Heart":78,"Time":678,"Name":"qianbo",
"Heart":75,"Time":679,"Name":"guanzhi",
"Heart":69,"Time":679,"Name":"guanzhi",
"Heart":72,"Time":679,"Name":"guanzhi",
"Heart":73,"Time":679,"Name":"guanzhi",
"Heart":70,"Time":679,"Name":"guanzhi"
]`
//var arr [2]Data
//json.Unmarshal([]byte(str), &s)
// data := make(map[string]interface)
// data["Name"] = "qianbo"
// data["Heart"] = 67
// data["Time"] = 778
// D := make(map[string]interface)
// D["Type"] = 1
// D["Data"] = data
// bytesData, err := json.Marshal(D)
// if err != nil
// fmt.Println(err.Error())
// return
//
// reader := bytes.NewReader(bytesData)
//request, err := http.NewRequest("POST", url, reader)
url := "http://127.0.0.1:8080/hrv"
var jsonStr = []byte(str)
request, err := http.NewRequest("POST", url, bytes.NewBuffer(jsonStr))
if err != nil
fmt.Println(err.Error())
return
request.Header.Set("Content-Type", "application/json;charset=UTF-8")
client := http.Client
resp, err := client.Do(request)
if err != nil
fmt.Println(err.Error())
return
body, err := ioutil.ReadAll(resp.Body)
if err != nil
fmt.Println(err.Error())
return
fmt.Println(string(body))
运行服务器
go run main.go
运行客户端测试
go run post.go
返回结果如下:
以上是关于使用go制作微服务数据计算的主要内容,如果未能解决你的问题,请参考以下文章