Exemplo n.º 1
0
// Intersects reports whether this points-to set and the
// argument points-to set contain common members.
func (x PointsToSet) Intersects(y PointsToSet) bool {
	if x.pts == nil || y.pts == nil {
		return false
	}
	// This takes Θ(|x|+|y|) time.
	var z intsets.Sparse
	z.Intersection(&x.pts.Sparse, &y.pts.Sparse)
	return !z.IsEmpty()
}
Exemplo n.º 2
0
func BenchmarkAppendTo(b *testing.B) {
	prng := rand.New(rand.NewSource(0))
	var x intsets.Sparse
	for i := 0; i < 1000; i++ {
		x.Insert(int(prng.Int()) % 10000)
	}
	var space [1000]int
	for tries := 0; tries < b.N; tries++ {
		x.AppendTo(space[:0])
	}
}
Exemplo n.º 3
0
// adds pb to the map literal -> pb.Id; as well as recording litSets
func addToCategory(nextId *int, pb *Threshold, cat map[sat.Literal][]int, lit2id map[sat.Literal]int, litSet *intsets.Sparse) {
	pb.Normalize(LE, true)
	for _, x := range pb.Entries {
		cat[x.Literal] = append(cat[x.Literal], pb.Id)
	}
	for _, e := range pb.Entries {
		if _, b := lit2id[e.Literal]; !b {
			lit2id[e.Literal] = *nextId
			*nextId++
		}
		litSet.Insert(lit2id[e.Literal])
	}
}
Exemplo n.º 4
0
func TestFailFastOnShallowCopy(t *testing.T) {
	var x intsets.Sparse
	x.Insert(1)

	y := x // shallow copy (breaks representation invariants)
	defer func() {
		got := fmt.Sprint(recover())
		want := "A Sparse has been copied without (*Sparse).Copy()"
		if got != want {
			t.Errorf("shallow copy: recover() = %q, want %q", got, want)
		}
	}()
	y.String() // panics
	t.Error("didn't panic as expected")
}
Exemplo n.º 5
0
func doChaining(pbs []*Threshold, complOcc map[sat.Literal][]int, simplOcc map[sat.Literal][]int,
	lit2id map[sat.Literal]int, litSets []intsets.Sparse) {

	//2) Prepare Matchings

	checked := make(map[Match]bool, 0)

	//ex_matchings := make(map[int][]Matching, 0)  // simpl_id -> []Matchings
	//currently ex and amo matchings are treated equivalently, the only
	//difference is that ex adds the unit clause of the ladder encoding, thus
	//the rewrite is correct and after UP the first value in the Ex is propagated.
	// TODO: explicitly rewrite and remove smallest value

	amo_matchings := make(map[int][]Matching, 0) // compl_id -> []Matchings

	for lit, list := range complOcc {
		//id2lit[lit2id[lit]] = lit
		for _, c := range list {
			for _, s := range simplOcc[lit] {
				if !checked[Match{c, s}] {
					// of comp c and simpl s there is at least
					checked[Match{c, s}] = true
					// 0 means it has not been checked,
					// as there is at least one intersection
					var inter intsets.Sparse
					inter.Intersection(&litSets[c], &litSets[s])
					if pbs[s].Typ == LE {
						if inter.Len() >= *glob.Len_rewrite_amo_flag {
							amo_matchings[c] = append(amo_matchings[c], Matching{s, &inter})
						}
					} else if pbs[s].Typ == EQ {
						if inter.Len() >= *glob.Len_rewrite_ex_flag {
							amo_matchings[c] = append(amo_matchings[c], Matching{s, &inter})
							//ex_matchings[c] = append(amo_matchings[c], Matching{s, &inter})
						}
					} else {
						glob.A(false, "case not treated")
					}
				}
			}
		}
	}

	glob.D("amo/ex_matchings:", len(amo_matchings))

	//3) amo/ex matchings

	for comp, _ := range pbs {
		if matchings, b := amo_matchings[comp]; b {
			workOnMatching(pbs, comp, matchings, lit2id, litSets)
		}
	}
}
func ArrayPairSum2(array []int, sum int) []IntPair {
	if len(array) < 2 {
		return nil
	}

	seen := intsets.Sparse{}
	result := make([]IntPair, 0, 100)
	for _, n := range array {
		target := sum - n
		if !seen.Has(target) {
			fmt.Printf("Insert: target=%d, n=%d, seen=%v\n", target, n, seen.String())
			seen.Insert(n)
		} else {
			fmt.Printf("Has: target=%d, n=%d, seen=%v\n", target, n, seen.String())
			result = append(result, IntPair{
				int(math.Min(float64(n), float64(target))),
				int(math.Max(float64(n), float64(target))),
			})
		}
	}
	return result
}
Exemplo n.º 7
0
// From returns all nodes in g that can be reached directly from u.
func (g Undirect) From(u Node) []Node {
	var (
		nodes []Node
		seen  intsets.Sparse
	)
	for _, n := range g.G.From(u) {
		seen.Insert(n.ID())
		nodes = append(nodes, n)
	}
	for _, n := range g.G.To(u) {
		id := n.ID()
		if seen.Has(id) {
			continue
		}
		seen.Insert(id)
		nodes = append(nodes, n)
	}
	return nodes
}
Exemplo n.º 8
0
func TestBitString(t *testing.T) {
	for _, test := range []struct {
		input []int
		want  string
	}{
		{nil, "0"},
		{[]int{0}, "1"},
		{[]int{0, 4, 5}, "110001"},
		{[]int{0, 7, 177}, "1" + strings.Repeat("0", 169) + "10000001"},
		{[]int{-3, 0, 4, 5}, "110001.001"},
		{[]int{-3}, "0.001"},
	} {
		var set intsets.Sparse
		for _, x := range test.input {
			set.Insert(x)
		}
		if got := set.BitString(); got != test.want {
			t.Errorf("BitString(%s) = %s, want %s", set.String(), got, test.want)
		}
	}
}
Exemplo n.º 9
0
func TestIntersects(t *testing.T) {
	prng := rand.New(rand.NewSource(0))

	for i := uint(0); i < 12; i++ {
		X, Y := randomPset(prng, 1<<i), randomPset(prng, 1<<i)
		x, y := &X.bits, &Y.bits

		// test the slow way
		var z intsets.Sparse
		z.Copy(x)
		z.IntersectionWith(y)

		if got, want := x.Intersects(y), !z.IsEmpty(); got != want {
			t.Errorf("Intersects: got %v, want %v", got, want)
		}

		// make it false
		a := x.AppendTo(nil)
		for _, v := range a {
			y.Remove(v)
		}

		if got, want := x.Intersects(y), false; got != want {
			t.Errorf("Intersects: got %v, want %v", got, want)
		}

		// make it true
		if x.IsEmpty() {
			continue
		}
		i := prng.Intn(len(a))
		y.Insert(a[i])

		if got, want := x.Intersects(y), true; got != want {
			t.Errorf("Intersects: got %v, want %v", got, want)
		}
	}
}
Exemplo n.º 10
0
func TestSubsetOf(t *testing.T) {
	prng := rand.New(rand.NewSource(0))

	for i := uint(0); i < 12; i++ {
		X, Y := randomPset(prng, 1<<i), randomPset(prng, 1<<i)
		x, y := &X.bits, &Y.bits

		// test the slow way
		var z intsets.Sparse
		z.Copy(x)
		z.DifferenceWith(y)

		if got, want := x.SubsetOf(y), z.IsEmpty(); got != want {
			t.Errorf("SubsetOf: got %v, want %v", got, want)
		}

		// make it true
		y.UnionWith(x)

		if got, want := x.SubsetOf(y), true; got != want {
			t.Errorf("SubsetOf: got %v, want %v", got, want)
		}

		// make it false
		if x.IsEmpty() {
			continue
		}
		a := x.AppendTo(nil)
		i := prng.Intn(len(a))
		y.Remove(a[i])

		if got, want := x.SubsetOf(y), false; got != want {
			t.Errorf("SubsetOf: got %v, want %v", got, want)
		}
	}
}
Exemplo n.º 11
0
func TestBasics(t *testing.T) {
	var s intsets.Sparse
	if len := s.Len(); len != 0 {
		t.Errorf("Len({}): got %d, want 0", len)
	}
	if s := s.String(); s != "{}" {
		t.Errorf("String({}): got %q, want \"{}\"", s)
	}
	if s.Has(3) {
		t.Errorf("Has(3): got true, want false")
	}
	if err := s.Check(); err != nil {
		t.Error(err)
	}

	if !s.Insert(3) {
		t.Errorf("Insert(3): got false, want true")
	}
	if max := s.Max(); max != 3 {
		t.Errorf("Max: got %d, want 3", max)
	}

	if !s.Insert(435) {
		t.Errorf("Insert(435): got false, want true")
	}
	if s := s.String(); s != "{3 435}" {
		t.Errorf("String({3 435}): got %q, want \"{3 435}\"", s)
	}
	if max := s.Max(); max != 435 {
		t.Errorf("Max: got %d, want 435", max)
	}
	if len := s.Len(); len != 2 {
		t.Errorf("Len: got %d, want 2", len)
	}

	if !s.Remove(435) {
		t.Errorf("Remove(435): got false, want true")
	}
	if s := s.String(); s != "{3}" {
		t.Errorf("String({3}): got %q, want \"{3}\"", s)
	}
}
Exemplo n.º 12
0
func TestTakeMin(t *testing.T) {
	var set intsets.Sparse
	set.Insert(456)
	set.Insert(123)
	set.Insert(789)
	set.Insert(-123)
	var got int
	for i, want := range []int{-123, 123, 456, 789} {
		if !set.TakeMin(&got) || got != want {
			t.Errorf("TakeMin #%d: got %d, want %d", i, got, want)
		}
	}
	if set.TakeMin(&got) {
		t.Errorf("%s.TakeMin returned true", &set)
	}
	if err := set.Check(); err != nil {
		t.Fatalf("check: %s: %#v", err, &set)
	}
}
Exemplo n.º 13
0
// Insert, Len, IsEmpty, Hash, Clear, AppendTo.
func TestMoreBasics(t *testing.T) {
	set := new(intsets.Sparse)
	set.Insert(456)
	set.Insert(123)
	set.Insert(789)
	if set.Len() != 3 {
		t.Errorf("%s.Len: got %d, want 3", set, set.Len())
	}
	if set.IsEmpty() {
		t.Errorf("%s.IsEmpty: got true", set)
	}
	if !set.Has(123) {
		t.Errorf("%s.Has(123): got false", set)
	}
	if set.Has(1234) {
		t.Errorf("%s.Has(1234): got true", set)
	}
	got := set.AppendTo([]int{-1})
	if want := []int{-1, 123, 456, 789}; fmt.Sprint(got) != fmt.Sprint(want) {
		t.Errorf("%s.AppendTo: got %v, want %v", set, got, want)
	}

	set.Clear()

	if set.Len() != 0 {
		t.Errorf("Clear: got %d, want 0", set.Len())
	}
	if !set.IsEmpty() {
		t.Errorf("IsEmpty: got false")
	}
	if set.Has(123) {
		t.Errorf("%s.Has: got false", set)
	}
}
Exemplo n.º 14
0
func (sb *SearchBotT) Search(searchBy map[string]string, searchFor []string, login string, password string, tid string) stonelizard.Response {
	var providers *intsets.Sparse
	var searchFields *intsets.Sparse
	var commonFields *intsets.Sparse
	var oneShotProviders *intsets.Sparse
	var field string
	var isFragmented bool
	var i int
	var p *TaxonomyTreeT
	var hasQueryParm bool
	var rep chan map[string]ResponseFieldT
	var response map[string]ResponseFieldT
	var responses map[string][]ResponseFieldT
	var respCount int

	//TODO: Readaptar
	searchBy["X-Login"] = login
	searchBy["X-Password"] = password
	searchBy["X-Trackid"] = tid

	//   Goose.Search = goose.Alert(6)
	//   defer func() { Goose.Search = goose.Alert(2) }()

	providers = &intsets.Sparse{}

	Goose.Search.Logf(2, "TID:%s len(sb.Providers): %d", tid, len(sb.Providers))

	// Fill the providers set with all provider currently known
	for i = 0; i < len(sb.Providers); i++ {
		providers.Insert(i)
	}

	// Determine if there is at least one bot providing all data needed
	// by repeatedly computing providers ∩= 'providers of a given field'
	for _, field = range searchFor {
		i, _, p = sb.Taxonomy.Search(field)
		if ((i + 1) != len(field)) || (p == nil) || (p.Id < 0) {
			Goose.Search.Logf(1, "TID:%s %s: %s", tid, ErrUndefinedField, field)
			return stonelizard.Response{
				Status: http.StatusInternalServerError,
				Body:   fmt.Sprintf("%s: %s", ErrUndefinedField, field),
			}
		}
		if sb.ByProvision[p.Id] == nil {
			isFragmented = true
			break
		}
		providers.IntersectionWith(sb.ByProvision[p.Id])
		if providers.IsEmpty() {
			isFragmented = true
			break
		}
	}

	Goose.Search.Logf(4, "TID:%s Determined if there is at least one bot providing all data needed (isFragmented=%#v): %#v", tid, isFragmented, providers)

	if !isFragmented {
		// Select in the bots that have all information needed
		// those who require only information we have
		searchFields = &intsets.Sparse{}
		for field, _ = range searchBy {
			i, _, p = sb.Taxonomy.Search(field)
			searchFields.Insert(p.Id)
		}

		Goose.Search.Logf(4, "TID:%s Bitstring of search created: %#v", tid, searchFields)

		oneShotProviders = &intsets.Sparse{}
		commonFields = &intsets.Sparse{}

		Goose.Search.Logf(4, "TID:%s providers.Max(): %d", tid, providers.Max())
		for i = 0; i <= providers.Max(); i++ {
			Goose.Search.Logf(4, "TID:%s Bitstring of sb.Providers[%d].Requires: %#v", tid, i, sb.Providers[i].Requires)
			commonFields.Intersection(searchFields, sb.Providers[i].Requires)
			if commonFields.Len() == sb.Providers[i].Requires.Len() {
				Goose.Search.Logf(4, "TID:%s Intersection at %d", tid, i)
				oneShotProviders.Insert(i)
			}
		}

		Goose.Search.Logf(4, "TID:%s Bitstring of oneShotProviders: %#v", tid, oneShotProviders)

		// If there is at least one bot who gives all fields
		// we need and requires just fields we already have...
		if oneShotProviders.Len() > 0 {
			rep = make(chan map[string]ResponseFieldT, oneShotProviders.Len())
			Goose.Search.Logf(4, "TID:%s len(sb.Providers): %d", tid, len(sb.Providers))
			for i = 0; i <= oneShotProviders.Max(); i++ {
				Goose.Search.Logf(4, "TID:%s oneShotProvider: %d", tid, i)
				if oneShotProviders.Has(i) {
					go func(instance int, report chan map[string]ResponseFieldT) {
						var err error
						var req *http.Request
						var host string
						var path string
						var swParm stonelizard.SwaggerParameterT
						var body map[string]interface{}
						var b_body []byte
						var resp *http.Response
						var qryResponse map[string]ResponseFieldT
						var nHost int
						//                  var buf             []byte
						//                  var n                 int

						Goose.Search.Logf(1, "TID:%s searching instance %d: ", tid, instance)

						defer func() { rep <- qryResponse }()

						for nHost = 0; nHost < len(sb.Providers[instance].Bot.Host); nHost++ {
							if sb.Providers[instance].Bot.Listen[0] == ':' {
								host = sb.Providers[instance].Bot.Host[nHost].Name
							} else {
								nHost = len(sb.Providers[instance].Bot.Host)
							}
							host = sb.Providers[instance].Operation.Schemes[0] + "://" + host + sb.Providers[instance].Bot.Listen

							path = sb.Providers[instance].Path
							body = map[string]interface{}{}

							Goose.Search.Logf(4, "TID:%s  Will add search path=%s, body=%#v", tid, path, body)
							Goose.Search.Logf(4, "TID:%s  Swagger reports the operation parameters are %#v", tid, sb.Providers[instance].Operation.Parameters)
							hasQueryParm = false
							for _, swParm = range sb.Providers[instance].Operation.Parameters {
								Goose.Search.Logf(3, "TID:%s  adding search parm: %s", tid, swParm.Name)
								if swParm.In == "path" {
									path = strings.Replace(path, "{"+swParm.Name+"}", searchBy[swParm.Name], -1)
									Goose.Search.Logf(3, "TID:%s path now is: %s", tid, path)
								} else if swParm.In == "query" {
									if !hasQueryParm {
										path += "?"
										hasQueryParm = true
									} else {
										path += "&"
									}
									path += swParm.Name + "=" + url.QueryEscape(searchBy[swParm.Name])
									Goose.Search.Logf(4, "TID:%s path now is: %#v", tid, path)
								} else if swParm.In == "body" {
									body[swParm.Name] = searchBy[swParm.Name]
									Goose.Search.Logf(4, "TID:%s body now is: %#v", tid, body)
								}
							}

							if sb.Providers[instance].Operation.Consumes[0] == "application/json" {
								b_body, err = json.Marshal(body)
							} else if sb.Providers[instance].Operation.Consumes[0] == "application/xml" {
								b_body, err = xml.Marshal(body)
							}

							if err != nil {
								Goose.Search.Logf(1, "TID:%s %s: %s", tid, ErrMarshalingRequestBody, err)
								return
							}

							Goose.Search.Logf(4, "TID:%s Requesting search via %s:%s%s with body=%#v", tid, sb.Providers[instance].HttpMethod, host, path, body)

							req, err = http.NewRequest(sb.Providers[instance].HttpMethod, host+path, bytes.NewReader(b_body))
							if err != nil {
								Goose.Search.Logf(1, "%s: %s", ErrAssemblyingRequest, err)
								return
							}

							for _, swParm = range sb.Providers[instance].Operation.Parameters {
								if swParm.In == "header" {
									if _, ok := req.Header[swParm.Name]; ok {
										req.Header[swParm.Name] = append(req.Header[swParm.Name], searchBy[swParm.Name])
									} else {
										req.Header[swParm.Name] = []string{searchBy[swParm.Name]}
									}

									//                           req.Header.Add(swParm.Name,searchBy[swParm.Name])
								}
							}

							resp, err = sb.HttpsSearchClient.Do(req)
							if err != nil {
								Goose.Search.Logf(1, "TID:%s %s: %s", tid, ErrQueryingSearchBot, err)
								continue // Let's try querying another instance of the search bots
							}

							/*
							   if resp.ContentLength > 0 {
							      b_body = make([]byte,resp.ContentLength)
							      err = io.ReadFull(resp.Body,b_body)
							   } else {
							      b_body = make([]byte,bufsz)
							      buf    = b_body
							      err    = nil
							      for err == nil {
							         n, err = resp.Body.Read(buf)
							         if (n==0) && (err==io.EOF) {
							            break
							         }
							         if (err!=nil) && (err!=io.EOF) {
							            Goose.Search.Logf(1,"TID:%s %s: %s",tid,ErrReadingResponseBody,err)
							            return
							         }
							         if n < bufsz {
							            b_body = b_body[:len(b_body)-(bufsz-n)]
							            break
							         }
							         b_body = append(b_body,...make([]byte,bufsz))
							         buf    = b_body[len(b_body)-bufsz:]
							      }
							   }
							*/
							//                     tmpbody, _ :=ioutil.ReadAll(resp.Body)
							//                     Goose.Search.Logf(4,"TID:%s Response: %s",tid,tmpbody)

							if sb.Providers[instance].Operation.Produces[0] == "application/json" {
								err = json.NewDecoder(resp.Body).Decode(&body)
							} else if sb.Providers[instance].Operation.Produces[0] == "application/xml" {
								err = xml.NewDecoder(resp.Body).Decode(&body)
							}

							Goose.Search.Logf(4, "TID:%s Response body: %#v", tid, body)

							if err != nil {
								Goose.Search.Logf(1, "TID:%s %s: %s", tid, ErrUnmarshalingRequestBody, err)
								return
							}

							qryResponse = map[string]ResponseFieldT{}
							for _, fieldName := range searchFor {
								Goose.Search.Logf(4, "TID:%s fetching Field %s: %#v", tid, fieldName, body[fieldName])
								Goose.Search.Logf(7, "TID:%s body[dtupdate]: %#v", tid, body["dtupdate"])
								Goose.Search.Logf(7, "TID:%s sb.Providers[instance].BotId: %#v", tid, sb.Providers[instance].BotId)
								Goose.Search.Logf(7, "TID:%s sb.Providers[instance].Bot.Host[nHost]: %#v", tid, sb.Providers[instance].Bot.Host[nHost])
								qryResponse[fieldName] = ResponseFieldT{
									Value:  body[fieldName],
									Source: sb.Providers[instance].BotId + "@" + sb.Providers[instance].Bot.Host[nHost].Name,
									DtUpd:  body["DtUpdate"].(string),
								}
							}

							Goose.Search.Logf(4, "TID:%s ResponseFieldT: %#v", tid, qryResponse)
							break
						}
					}(i, rep)
				}
			}

			responses = map[string][]ResponseFieldT{}
			for respCount < oneShotProviders.Len() {
				Goose.Search.Logf(4, "TID:%s Waiting response %d/%d", tid, respCount, oneShotProviders.Len())
				response = <-rep
				respCount++
				if response != nil {
					Goose.Search.Logf(4, "TID:%s Got response from bot: %#v", tid, response)
					for k, v := range response {
						if _, ok := responses[k]; ok {
							responses[k] = append(responses[k], v)
						} else {
							responses[k] = []ResponseFieldT{v}
						}
					}
				} else {
					Goose.Search.Logf(1, "TID:%s Bot instance failed", tid)
				}
			}

			Goose.Search.Logf(4, "TID:%s Final consolidated ResponseFieldT: %#v", tid, responses)
			return stonelizard.Response{
				Status: http.StatusOK,
				Body:   responses,
			}
		}
	}

	/*
	   if !isFragmented {
	      for i=0; i < providers.Max(); i++ {
	         if providers.Has(i) {
	            go func(instance int) {
	               sb.HttpsSearchClient.Get(sb.Providers[i])
	            }(i)
	         }
	      }
	   }
	*/

	return stonelizard.Response{
		Status: http.StatusOK,
		Body:   "Unimplemented yet!",
	}
}
Exemplo n.º 15
0
func BenchmarkSparseBitVector(b *testing.B) {
	prng := rand.New(rand.NewSource(0))
	for tries := 0; tries < b.N; tries++ {
		var x, y, z intsets.Sparse
		for i := 0; i < 1000; i++ {
			n := int(prng.Int()) % 100000
			if i%2 == 0 {
				x.Insert(n)
			} else {
				y.Insert(n)
			}
		}
		z.Union(&x, &y)
		z.Difference(&x, &y)
	}
}
Exemplo n.º 16
0
func TestMinAndMax(t *testing.T) {
	values := []int{0, 456, 123, 789, -123} // elt 0 => empty set
	wantMax := []int{intsets.MinInt, 456, 456, 789, 789}
	wantMin := []int{intsets.MaxInt, 456, 123, 123, -123}

	var set intsets.Sparse
	for i, x := range values {
		if i != 0 {
			set.Insert(x)
		}
		if got, want := set.Min(), wantMin[i]; got != want {
			t.Errorf("Min #%d: got %d, want %d", i, got, want)
		}
		if got, want := set.Max(), wantMax[i]; got != want {
			t.Errorf("Max #%d: got %d, want %d", i, got, want)
		}
	}

	set.Insert(intsets.MinInt)
	if got, want := set.Min(), intsets.MinInt; got != want {
		t.Errorf("Min: got %d, want %d", got, want)
	}

	set.Insert(intsets.MaxInt)
	if got, want := set.Max(), intsets.MaxInt; got != want {
		t.Errorf("Max: got %d, want %d", got, want)
	}
}
Exemplo n.º 17
0
func TestEquals(t *testing.T) {
	var setX intsets.Sparse
	setX.Insert(456)
	setX.Insert(123)
	setX.Insert(789)

	if !setX.Equals(&setX) {
		t.Errorf("Equals(%s, %s): got false", &setX, &setX)
	}

	var setY intsets.Sparse
	setY.Insert(789)
	setY.Insert(456)
	setY.Insert(123)

	if !setX.Equals(&setY) {
		t.Errorf("Equals(%s, %s): got false", &setX, &setY)
	}

	setY.Insert(1)
	if setX.Equals(&setY) {
		t.Errorf("Equals(%s, %s): got true", &setX, &setY)
	}

	var empty intsets.Sparse
	if setX.Equals(&empty) {
		t.Errorf("Equals(%s, %s): got true", &setX, &empty)
	}

	// Edge case: some block (with offset=0) appears in X but not Y.
	setY.Remove(123)
	if setX.Equals(&setY) {
		t.Errorf("Equals(%s, %s): got true", &setX, &setY)
	}
}
Exemplo n.º 18
0
// deltaQ returns the highest gain in modularity attainable by moving
// n from its current community to another connected community and
// the index of the chosen destination. The index into the localMover's
// communities field is returned in src if n is in communities.
func (l *localMover) deltaQ(n graph.Node) (deltaQ float64, dst int, src commIdx) {
	id := n.ID()
	a_aa := l.weight(n, n)
	k_a := l.edgeWeightOf[id]
	m2 := l.m2
	gamma := l.resolution

	// Find communites connected to n.
	var connected intsets.Sparse
	// The following for loop is equivalent to:
	//
	//  for _, v := range l.g.From(n) {
	//  	connected.Insert(l.memberships[v.ID()])
	//  }
	//
	// This is done to avoid an allocation.
	for _, vid := range l.g.edges[id] {
		connected.Insert(l.memberships[vid])
	}
	// Insert the node's own community.
	connected.Insert(l.memberships[id])

	// Calculate the highest modularity gain
	// from moving into another community and
	// keep the index of that community.
	var dQremove float64
	dQadd, dst, src := math.Inf(-1), -1, commIdx{-1, -1}
	var i int
	for connected.TakeMin(&i) {
		c := l.communities[i]
		var k_aC, sigma_totC float64 // C is a substitution for ^𝛼 or ^𝛽.
		var removal bool
		for j, u := range c {
			uid := u.ID()
			if uid == id {
				if src.community != -1 {
					panic("community: multiple sources")
				}
				src = commIdx{i, j}
				removal = true
			}

			k_aC += l.weight(n, u)
			// sigma_totC could be kept for each community
			// and updated for moves, changing the calculation
			// of sigma_totC here from O(n_c) to O(1), but
			// in practice the time savings do not appear
			// to be compelling and do not make up for the
			// increase in code complexity and space required.
			sigma_totC += l.edgeWeightOf[uid]
		}

		// See louvain.tex for a derivation of these equations.
		switch {
		case removal:
			// The community c was the current community,
			// so calculate the change due to removal.
			dQremove = 2*(k_aC /*^𝛼*/ -a_aa) - 2*gamma*k_a*(sigma_totC /*^𝛼*/ -k_a)/m2

		default:
			// Otherwise calculate the change due to an addition
			// to c and retain if it is the current best.
			dQ := 2*k_aC /*^𝛽*/ - 2*gamma*k_a*sigma_totC /*^𝛽*/ /m2
			if dQ > dQadd {
				dQadd = dQ
				dst = i
			}
		}
	}

	return (dQadd - dQremove) / m2, dst, src
}
Exemplo n.º 19
0
func computeChainFrom(from, to canvas.Node) (chain []canvas.NodeIfc) {
	// For each link, there is a chain of modules to be invoked: the
	// ingress policy modules, the egress policy modules, and the final
	// forwarding nexthop.
	//
	// To compute the chain in each direction, the following algorithm is
	// followed:
	//  Let T and F represent the set of groups for the 'to' and 'from'
	//   nodes, respectively.
	//  The leaving set L is the set difference between F and T.
	//  L := F - T
	//  The entering set E is the set difference between T and F
	//  E := T - F
	//
	// For the directed edge from:to, the chain is built as follows:
	//  For each module e in E, invoke the ingress policy (e.ifc[1])
	//  For each module l in L, invoke the egress policy (l.ifc[2])
	//
	// The directed edge to:from is calculated by calling this function
	// with to/from reversed.

	var e, l, x intsets.Sparse
	l.Difference(from.Groups(), to.Groups())
	e.Difference(to.Groups(), from.Groups())

	var id int

	x.Copy(&e)
	for x.TakeMin(&id) {
		chain = append(chain, canvas.NodeIfc{id, 1})
	}
	x.Copy(&l)
	for x.TakeMin(&id) {
		chain = append(chain, canvas.NodeIfc{id, 2})
	}
	return chain
}
Exemplo n.º 20
0
func TestIntersectionWith(t *testing.T) {
	// Edge cases: the pairs (1,1), (1000,2000), (8000,4000)
	// exercise the <, >, == cases in IntersectionWith that the
	// TestSetOperations data is too dense to cover.
	var X, Y intsets.Sparse
	X.Insert(1)
	X.Insert(1000)
	X.Insert(8000)
	Y.Insert(1)
	Y.Insert(2000)
	Y.Insert(4000)
	X.IntersectionWith(&Y)
	if got, want := X.String(), "{1}"; got != want {
		t.Errorf("IntersectionWith: got %s, want %s", got, want)
	}
}