| | |
| | | import ( |
| | | "ruleprocess/cache" |
| | | "ruleprocess/structure" |
| | | "basic.com/valib/logger.git" |
| | | "ruleprocess/logger" |
| | | "sort" |
| | | "strconv" |
| | | "strings" |
| | |
| | | |
| | | if result.(bool) { |
| | | // 最后过持续时间等时间维度的条件 把时间规则位置调整到这个位置是为了缓存数据 |
| | | cacheId := "" |
| | | for j := 0; j < len(groupRule.Rules); j++ { |
| | | for _, sdkData := range args.Sdkdata { |
| | | sdk, err := cache.GetSdkById(groupRule.Rules[j].SdkId) |
| | |
| | | if ipcId == sdkData.IpcId { |
| | | for _, areaMap := range sdkData.AreaMapList { |
| | | // 去开启一个定时器 |
| | | duration(groupRule.Rules[j], groupRule.GroupId, areaMap, args, message) |
| | | cacheid := duration(groupRule.Rules[j], groupRule.GroupId, areaMap, args, message) |
| | | if cacheid != "" { |
| | | cacheId = cacheid |
| | | } |
| | | } |
| | | } |
| | | } |
| | | } |
| | | // 进行定时器的处理和判断 |
| | | timeFlag := TimerAlarm(&label, groupRule.GroupId, result.(bool)) |
| | | if timeFlag == "01" || timeFlag == "10" || timeFlag == "11" { // 没有定时器或者满足定时器条件 |
| | | if timeFlag == "01" || timeFlag == "10" || timeFlag == "11" || cacheId != ""{ // 没有定时器或者满足定时器条件 |
| | | // 打人脸标签和yolo标签 |
| | | // 最后成功报警才把符合条件的人脸数据塞进结果标签里 |
| | | // 配了人脸的算法才把人脸的数据甩出来打标签 |
| | |
| | | } |
| | | } |
| | | } |
| | | logger.Info("face标签的长度:",len(faces)) |
| | | //logger.Info("face标签的长度:",len(faces)) |
| | | //for _,face := range faces { |
| | | // //logger.Debug("————————————————________________看看人脸的坐标:",face.Location) |
| | | //} |
| | |
| | | //logger.Info("-------------------face结果标签", len(args.RuleResult["face"].([]FaceResult))) |
| | | labelTypes = append(labelTypes,1) |
| | | } |
| | | // 给持续时间的第一张赋予缓存数据(遍历复制) |
| | | if cacheId != "" { // 有这帧数据的缓存 |
| | | tempMap := make(map[string]interface{}) |
| | | for k, result := range args.RuleResult { |
| | | if k == "yolo" { |
| | | tempMap[k] = []structure.Result{} |
| | | for _, res := range result.([]structure.Result) { |
| | | tempMap[k] = append(tempMap[k].([]structure.Result), res) |
| | | } |
| | | } |
| | | if k == "face" { |
| | | tempMap[k] = []structure.FaceResult{} |
| | | for _, res := range result.([]structure.FaceResult) { |
| | | tempMap[k] = append(tempMap[k].([]structure.FaceResult), res) |
| | | } |
| | | } |
| | | } |
| | | rw.Lock() |
| | | TimeEleList[cacheId].CacheSdkData.RuleResult = tempMap |
| | | rw.Unlock() |
| | | } |
| | | |
| | | return true,labelTypes |
| | | } else { |
| | | return false,[]int{} |
| | |
| | | timeEle = *timeEle1 |
| | | } |
| | | } |
| | | for _,ruleRe := range timeEle.RuleResults { |
| | | logger.Info("联动数组里的数据----",ruleRe.CameraId,ruleRe.Sort) |
| | | } |
| | | //for _,ruleRe := range timeEle.RuleResults { |
| | | // logger.Info("联动数组里的数据----",ruleRe.CameraId,ruleRe.Sort) |
| | | //} |
| | | if flag { // 如果还没有这个定时器元素就新增一个 |
| | | //timeEle := TimeElement{N: 2, InitN: 2, GroupId: groupRule.GroupId} // 扔进去一个定时器元素 |
| | | //TimeEleList = make(map[string]timeElement) |
| | | TimeEleList[groupRule.GroupId] = &timeEle // 定时器元素以规则组id为键 |
| | | logger.Info("---------------------------------------------联动任务创建了计数器并且计数器集合为:", TimeEleList) |
| | | //logger.Info("---------------------------------------------联动任务创建了计数器并且计数器集合为:", TimeEleList) |
| | | // 得出这组完整规则里涉及到几个摄像机,决定着数组里有几个结构体,去重添加方式 |
| | | for j := 0; j < len(groupRule.Rules); j++ { |
| | | var flag1 bool = true |
| | | logger.Info("规则组信息:",groupRule.Rules[j].CameraId) |
| | | //logger.Info("规则组信息:",groupRule.Rules[j].CameraId) |
| | | for _, ruleRes := range TimeEleList[groupRule.GroupId].RuleResults { |
| | | logger.Info("联动数组里的数据:",ruleRes.CameraId,ruleRes.Sort) |
| | | //logger.Info("联动数组里的数据:",ruleRes.CameraId,ruleRes.Sort) |
| | | if groupRule.Rules[j].CameraId == ruleRes.CameraId { |
| | | flag1 = false |
| | | } |
| | |
| | | for _, ruleRes := range TimeEleList[groupRule.GroupId].RuleResults { |
| | | label.LinkCache = append(label.LinkCache, ruleRes.CacheData) |
| | | } |
| | | logger.Debug("联动任务缓存了几个数据", len(label.LinkCache)) |
| | | //logger.Debug("联动任务缓存了几个数据", len(label.LinkCache)) |
| | | for i := 0; i < len(args.RuleResult["yolo"].([]structure.Result)); i++ { |
| | | if args.RuleResult["yolo"].([]structure.Result)[i].RuleGroupId == groupRule.GroupId { // 把联动数据追加上 |
| | | args.RuleResult["yolo"].([]structure.Result)[i].Others.LinkCache = label.LinkCache |
| | |
| | | // 把没有相似者的人脸从filterData中删除 |
| | | for index := 0; index < len(am.FilterData); { |
| | | // 将达不到阈值的相似者从相似者数组中删除 |
| | | logger.Info("看看相似者人数:",len(am.FilterData[index].Liker)) |
| | | //logger.Info("看看相似者人数:",len(am.FilterData[index].Liker)) |
| | | if len(am.FilterData[index].Liker) == 0 { |
| | | // Go 语言中切片删除元素的本质是:以被删除元素为分界点,将前后两个部分的内存重新连接起来。不用怀疑,数组删除元素就这么坑爹 |
| | | am.FilterData = append(am.FilterData[:index], am.FilterData[index+1:]...) |
| | |
| | | if len(am.FilterData) > 0 { |
| | | flag = "true" |
| | | } |
| | | logger.Info("---------人脸比对符合条件的数量为:",len(am.FilterData)) |
| | | //logger.Info("---------人脸比对符合条件的数量为:",len(am.FilterData)) |
| | | return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + flag, rule.Sort} |
| | | } |
| | | } |
| | |
| | | if rule.Operator == "==" || rule.Operator == ">=" || rule.Operator == "<=" || rule.Operator == "<" || rule.Operator == ">" || rule.Operator == "!=" { |
| | | // 如果是不规矩的连接符统统返回false 规则也只能判断人脸的相似度,所以不存在别的连接符 |
| | | if rule.SdkArgAlias == "score" || rule.SdkArgAlias == "proportion" || rule.SdkArgAlias == "size" { // 判断的是相似值,占比,尺寸等过滤条件,如果再有,还可以再加 |
| | | logger.Info("-----------------------过规则之前区域内的人脸数量为:",am.TargetNum) |
| | | //logger.Info("-----------------------过规则之前区域内的人脸数量为:",am.TargetNum) |
| | | var args []*structure.Arg |
| | | if rule.RuleWithPre == "&&" { |
| | | args = am.FilterData |
| | |
| | | } |
| | | } |
| | | am.TargetNum = len(am.FilterData) // 把符合条件的目标数量更新到targetNum字段 |
| | | logger.Info("过完条件后的目标数量为:",am.TargetNum) |
| | | //logger.Info("过完条件后的目标数量为:",am.TargetNum) |
| | | if am.TargetNum > 0 { |
| | | logger.Info("!!!!!!!!!人脸检测成功") |
| | | return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + "true", rule.Sort} |
| | |
| | | } |
| | | |
| | | // 如果有持续时间条件维护开启一个定时器 |
| | | func duration(rule *protomsg.Rule, groupId string, am *structure.AreaMap, args *structure.SdkDatas, message *protomsg.SdkMessage) { |
| | | func duration(rule *protomsg.Rule, groupId string, am *structure.AreaMap, args *structure.SdkDatas, message *protomsg.SdkMessage) string{ |
| | | cacheId := "" |
| | | if rule.PolygonId == am.AreaId { // 首先规则所对应的区域id要跟区域数据的id对的上 配置的算法要对的上 |
| | | if rule.SdkArgAlias == "duration" { // |
| | | logger.Info("当前小规则是:---------", rule) |
| | | //logger.Info("当前小规则是:---------", rule) |
| | | // 先看看定时器元素队列中是否有这条规则的定时器,如果有就不能再次创建了 |
| | | rw.Lock() |
| | | var flag bool = true |
| | | for k, _ := range TimeEleList { |
| | | if k == groupId+"+"+rule.Id { |
| | | flag = false // 有就置为false |
| | | logger.Info("有这个定时器,不再创建了:") |
| | | //logger.Info("有这个定时器,不再创建了:") |
| | | } |
| | | } |
| | | |
| | | if flag { |
| | | timeLength, _ := strconv.Atoi(rule.SdkArgValue) |
| | | timeEle := TimeElement{N: timeLength, InitN: timeLength, AlarmFlag: false, BufferFlag: 10, CacheSdkData: structure.ResultMsg{message, args.RuleResult}} // 扔进去一个定时器元素(并缓存当前画面帧数据) |
| | | timeEle := TimeElement{N: timeLength, InitN: timeLength, AlarmFlag: false, BufferFlag: 10, CacheSdkData: structure.ResultMsg{message, nil}} // 扔进去一个定时器元素(并缓存当前画面帧数据) |
| | | //TimeEleList = make(map[string]timeElement) |
| | | TimeEleList[groupId+"+"+rule.Id] = &timeEle // 定时器元素以当前持续时间小规则id为键 |
| | | logger.Info("创建了计数器") |
| | | cacheId = groupId+"+"+rule.Id |
| | | } |
| | | rw.Unlock() |
| | | } |
| | | } |
| | | return cacheId |
| | | } |
| | | |
| | | // 给数据库的规则表达式代参 args: 一条子规则,区域数据 |