diff --git a/search.go b/search.go index ce1a49d..90f5277 100644 --- a/search.go +++ b/search.go @@ -65,15 +65,20 @@ func (DB *Search) Replace(list []string) { func (DB *Search) Match(Title string) []interface{} { IDS := []ID{} title := DB.CleanSearch(strings.ToLower(Title)) -mainLoop: for k, v := range DB.Words { + tempKeys := []ID{} for _, t := range v { sim := similarity(t, title) if sim > 0 { - IDS = append(IDS, ID{Key: k, Score: sim, Title: t}) - continue mainLoop + tempKeys = append(tempKeys, ID{Key: k, Score: sim, Title: t}) } } + if len(tempKeys) > 0 { + sort.Slice(tempKeys, func(i, j int) bool { + return tempKeys[i].Score > tempKeys[j].Score + }) + IDS = append(IDS, tempKeys[0]) + } } sort.Slice(IDS, func(i, j int) bool { return IDS[i].Score > IDS[j].Score @@ -96,8 +101,8 @@ loop: s++ matched = append(matched, f) continue loop - } else { - s = s - 0.125 + } else if i != l { + s = s - ((float64(len(i)) * 0.1) * (0.125 / 2)) } } } diff --git a/search_test.go b/search_test.go new file mode 100644 index 0000000..fed084d --- /dev/null +++ b/search_test.go @@ -0,0 +1,63 @@ +package search + +import ( + "git.fuyu.moe/Fuyu/assert" + "strings" + "testing" +) + +func TestAdd(t *testing.T) { + var DB Search + as := assert.New(t) + for i := 0; i < 50; i++ { + DB.Add(i, [][]string{[]string{"test"}, []string{"another", "test"}, []string{"third", "one"}}) + } + + as.Eq("test", DB.Words[0][0][0]) + as.Contains("another", DB.Words[0][1]) + as.Eq(50, len(DB.Words)) +} + +func TestMatch(t *testing.T) { + var DB Search + as := assert.New(t) + DB.Add(2, [][]string{[]string{"test"}, []string{"another", "test"}, []string{"third", "one"}}) + DB.Add(1, [][]string{[]string{"test"}, []string{"another", "test"}, []string{"third", "test"}}) + res := DB.Match("third") + as.Eq(2, res[0]) + as.Eq(2, len(res)) +} + +func TestCleanSearch(t *testing.T) { + var DB Search + as := assert.New(t) + as.SameElements(DB.CleanSearch("Title of a anime in here"), []string{`title`, `of`, `a`, `anime`, `in`, `here`}) +} + +func TestIgnore(t *testing.T) { + var DB Search + as := assert.New(t) + expectedIgnored := []string{`a`, `of`, `in`, `the`, `wa`, `ga`, `no`, `ni`, `wo`, `he`, `o`, `ka`} + DB.Ignore(expectedIgnored) + as.SameElements(expectedIgnored, DB.IgnoreWords) + as.SameElements(DB.CleanSearch("Title of a anime in here"), []string{`title`, `anime`, `here`}) +} + +func TestReplace(t *testing.T) { + var DB Search + as := assert.New(t) + expectedReplace := strings.Split(`〜☆♪・〈〉「」!『』²Ⅱ+[](),.!?\/{}+-_=~"'@#$%^&*|;:<>`, ``) + DB.Replace(expectedReplace) + as.SameElements(expectedReplace, DB.RemoveCharacters) + as.SameElements(DB.CleanSearch("Ti☆tle〜 of☆a anime² in♪ 「here」"), []string{`ti`, `tle`, `of`, `a`, `anime`, `in`, `here`}) +} + +func BenchmarkMatch(b *testing.B) { + var DB Search + for i := 0; i < 10000; i++ { + DB.Add(i, [][]string{[]string{string(i)}, []string{"another", "test" + string(i)}, []string{"third", "test"}}) + } + for n := 0; n < b.N; n++ { + DB.Match(`5`) + } +}