add rlock in shardmap walk
| | |
| | | func (s *ShardMap) Walk(wf wfOp, sourceFea []float32, baseScore float32) (targets []*protomsg.SdkCompareEach) { |
| | | var wg sync.WaitGroup |
| | | var lock sync.Mutex |
| | | //fmt.Printf("Walk shards len %d\n", len(s.shards)) |
| | | |
| | | for _, si := range s.shards { |
| | | var tempsi shardItem = *si |
| | | var tempsi *shardItem = si // 保持对原始 shardItem 的指针引用 |
| | | |
| | | // 跳过空分片 |
| | | if len(tempsi.data) == 0 { |
| | | continue |
| | | } |
| | | |
| | | wg.Add(1) |
| | | |
| | | go func(st *shardItem, fn wfOp, srcFeat []float32, baseSec float32) { |
| | | defer wg.Done() |
| | | st.RLock() // 锁定读取 |
| | | defer st.RUnlock() // 确保读取完毕后解锁 |
| | | |
| | | for _, feature := range st.data { |
| | | // 读取操作在锁内进行,防止并发冲突 |
| | | if item, ok := feature.(*db.FeatureCacheBase); ok { |
| | | score := float32(0) |
| | | score = fn(srcFeat, item.FaceFeature) |
| | | score := fn(srcFeat, item.FaceFeature) |
| | | if score > 0 && score >= baseScore { |
| | | lock.Lock() |
| | | lock.Lock() // 保护目标切片的写入 |
| | | targets = append(targets, &protomsg.SdkCompareEach{ |
| | | Id: item.Id, |
| | | CompareScore: score, |
| | |
| | | } |
| | | } |
| | | } |
| | | |
| | | }(&tempsi, wf, sourceFea, baseScore) |
| | | }(tempsi, wf, sourceFea, baseScore) |
| | | } |
| | | |
| | | wg.Wait() |
| | | return targets |
| | | |
| | | } |
| | | |
| | | // print all |