func cacheExtsEmbs(dt *Digraph, pattern *subgraph.SubGraph, support int, exts []*subgraph.Extension, embs []*subgraph.Embedding, overlap []map[int]bool, unsupEmbs subgraph.VertexEmbeddings) error { if dt.Mode&Caching == 0 { return nil } dt.lock.Lock() defer dt.lock.Unlock() label := pattern.Label() // frequency will always get added, so if frequency has the label // this pattern has already been saved if has, err := dt.Frequency.Has(label); err != nil { return err } else if has { return nil } err := dt.Frequency.Add(label, int32(support)) if err != nil { return nil } // if the support is too low we can bail on saving the rest of the // node if support < dt.Support() { return nil } // save the supported extensions and embeddings for _, ext := range exts { err := dt.Extensions.Add(label, ext) if err != nil { return err } } for _, emb := range embs { err := dt.Embeddings.Add(emb.SG, emb) if err != nil { return err } } if dt.Overlap != nil && len(pattern.E) > 3 { // save the overlap if using err = dt.Overlap.Add(pattern, overlap) if err != nil { return err } } if dt.UnsupEmbs != nil { // for _, emb := range unsupEmbs { // err = dt.UnsupEmbs.Add(pattern, emb) // if err != nil { // return err // } // } } return nil }
func isCanonicalExtension(cur *subgraph.SubGraph, ext *subgraph.SubGraph) (bool, error) { // errors.Logf("DEBUG", "is %v a canonical ext of %v", ext.Label(), n) parent, err := firstParent(subgraph.Build(len(ext.V), len(ext.E)).From(ext)) if err != nil { return false, err } else if parent == nil { return false, errors.Errorf("ext %v of node %v has no parents", ext, cur) } if bytes.Equal(parent.Build().Label(), cur.Label()) { return true, nil } return false, nil }
func loadCachedExtsEmbs(dt *Digraph, pattern *subgraph.SubGraph) (bool, int, []*subgraph.Extension, []*subgraph.Embedding, []map[int]bool, subgraph.VertexEmbeddings, error) { if dt.Mode&Caching == 0 { return false, 0, nil, nil, nil, nil, nil } dt.lock.RLock() defer dt.lock.RUnlock() label := pattern.Label() if has, err := dt.Frequency.Has(label); err != nil { return false, 0, nil, nil, nil, nil, err } else if !has { return false, 0, nil, nil, nil, nil, nil } support := 0 err := dt.Frequency.DoFind(label, func(_ []byte, s int32) error { support = int(s) return nil }) if err != nil { return false, 0, nil, nil, nil, nil, err } exts := make([]*subgraph.Extension, 0, 10) err = dt.Extensions.DoFind(label, func(_ []byte, ext *subgraph.Extension) error { exts = append(exts, ext) return nil }) if err != nil { return false, 0, nil, nil, nil, nil, err } embs := make([]*subgraph.Embedding, 0, 10) err = dt.Embeddings.DoFind(pattern, func(_ *subgraph.SubGraph, emb *subgraph.Embedding) error { embs = append(embs, emb) return nil }) if err != nil { return false, 0, nil, nil, nil, nil, err } var overlap []map[int]bool = nil if dt.Overlap != nil { err = dt.Overlap.DoFind(pattern, func(_ *subgraph.SubGraph, o []map[int]bool) error { overlap = o return nil }) if err != nil { return false, 0, nil, nil, nil, nil, err } } var unsupEmbs subgraph.VertexEmbeddings = nil if dt.UnsupEmbs != nil { // unsupEmbs = make([]*subgraph.Embedding, 0, 10) // err = dt.Embeddings.DoFind(pattern, func(_ *subgraph.SubGraph, emb *subgraph.Embedding) error { // unsupEmbs = append(unsupEmbs, emb) // return nil // }) // if err != nil { // return false, 0, nil, nil, nil, nil, err // } } return true, support, exts, embs, overlap, unsupEmbs, nil }