diff --git a/util/sort/CountingSort.go b/util/sort/CountingSort.go new file mode 100644 index 0000000..fd73e9a --- /dev/null +++ b/util/sort/CountingSort.go @@ -0,0 +1,47 @@ +/* + * @Author : huangzj + * @Time : 2020/8/21 9:28 + * @Description:计数排序,时间复杂度:Ο (n+k)、空间复杂度是 O(k) + * 限制:1.当数列最大最小值差距过大时,并不适用计数排序。2.当数列元素不是整数,并不适用计数排序。 + * 参考地址:https://blog.csdn.net/csdnnews/article/details/83005778 + */ + +package sort + +import "math" + +func CountingSort(list []int) []int { + min, max := findMinAndMax(list) + countArray := make([]int, max-min+1) + for index := range list { + countArray[list[index]-min]++ //根据偏移量对数组某个下标的元素进行增一,如果这个位置元素存在 + } + + //创建结果数组,这边其实可以直接输出或者使用原来的数组 + result := make([]int, len(list)) + pos := 0 + for index := range countArray { + for countArray[index] != 0 { + result[pos] = index + min + pos++ + countArray[index]-- + } + } + + return result +} + +func findMinAndMax(list []int) (int, int) { + min := math.MaxInt64 + max := math.MinInt64 + //找到数组中的最大值和最小值 + for _, num := range list { + if num > max { + max = num + } + if num < min { + min = num + } + } + return min, max +} diff --git a/util/sort/CountingSort_test.go b/util/sort/CountingSort_test.go new file mode 100644 index 0000000..683cbda --- /dev/null +++ b/util/sort/CountingSort_test.go @@ -0,0 +1,43 @@ +/* + * @Author : huangzj + * @Time : 2020/8/21 9:28 + * @Description: + */ + +package sort + +import ( + "fmt" + "testing" +) + +func TestCountingSort(t *testing.T) { + list1 := []int{1, 2, 3, 4, 5, 6, 7, 8, 9, 10} + CountingSort(list1) + for _, r := range list1 { + fmt.Print(r, " ") + } + fmt.Println() + + list2 := []int{10, 9, 8, 7, 6, 5, 4, 3, 2, 1} + result2 := CountingSort(list2) + for _, r := range result2 { + fmt.Print(r, " ") + } + fmt.Println() + + list3 := []int{1, 432, 12, 67, 341, 874, 56332, 43, 6564, 234, 980, 4234, 6589932, 80, 42, 4234, 55} + result3 := CountingSort(list3) + for _, r := range result3 { + fmt.Print(r, " ") + } + fmt.Println() + + list4 := []int{4523325, 21, 43, 1, 265, 7657, 8754, 234, 543, 536, 2, 6543, 772, 432, 5, 6, 7214, 6754} + result4 := CountingSort(list4) + for _, r := range result4 { + fmt.Print(r, " ") + } + fmt.Println() + +} diff --git a/util/stringMatch/HorspoolMatch.go b/util/stringMatch/HorspoolMatch.go new file mode 100644 index 0000000..e658654 --- /dev/null +++ b/util/stringMatch/HorspoolMatch.go @@ -0,0 +1,53 @@ +/* + * @Author : huangzj + * @Time : 2020/8/21 16:06 + * @Description:参考地址:http://www.ifcoding.com/archives/247.html + * 该算法相当于先构造出对应的字符的移动位置,这边假设只匹配字母,则构造26个字母的移动表 + * 从匹配的字符串的最后一位开始跟被匹配字符串进行匹配,直到没有匹配的字段或者匹配完整之后结束 + * 得到当前匹配不正确的那个位置的字母,以此来找到该字母对应的移动位置,然后把匹配的字符串向后移动对应的位置,使得该字母和后面的字母对上,然后再进行一次匹配,直到找到对应的字符串位置为止,或者没有匹配的字符串返回-1 + * 举例 abcdefg 和 bcd进行匹配 + * 第一次: abcdefg + * d + * 发现不匹配并且不匹配的字母是c,所以按照c的移动规则,向后移动一位 + * 第二次: abcdefg + * cd + * + * abcdefg + * bcd + * 关于另一种更有效的模式匹配算法 Boyer-Moore这边不给出算法实现(比较复杂),可参考:https://www.cnblogs.com/en-heng/p/5095542.html + */ + +package stringMatch + +func Horspool(allString string, match string) int { + //生成对应的移动表数据 + move := shiTable(match) + i := len(match) - 1 + for i < len(allString) { + k := 0 + for k < len(match) && match[len(match)-1-k] == allString[i-k] { + k++ + } + if k == len(match) { + return i - len(match) + 1 + } else { + i = i + move[allString[i]-'a'] + } + } + + return -1 +} + +//生成对应的移动表数据 +func shiTable(s string) []int { + table := make([]int, 27) //这边只考虑26个字母和一个空字符串的情况 + //所有格子都初始化移动步数为被查找字符串长度. + for i := 0; i < 27; i++ { + table[i] = len(s) + } + //构造对应的被查找字符串中的字符的移动步数 + for i := 0; i < len(s)-1; i++ { + table[s[i]-'a'] = len(s) - 1 - i + } + return table +} diff --git a/util/stringMatch/HorspoolMatch_test.go b/util/stringMatch/HorspoolMatch_test.go new file mode 100644 index 0000000..b40994c --- /dev/null +++ b/util/stringMatch/HorspoolMatch_test.go @@ -0,0 +1,26 @@ +/* + * @Author : huangzj + * @Time : 2020/8/21 16:07 + * @Description: + */ + +package stringMatch + +import ( + "fmt" + "testing" +) + +func TestHorspool(t *testing.T) { + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "abcd")) //输出0 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "bcd")) //输出1 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "fgh")) //输出6 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "hijk")) //输出8 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "jk")) //输出10 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "k")) //输出11 + + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "kbz")) //输出-1 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "kdasdsad")) //输出-1 + fmt.Println("该子串的位置为:", Horspool("abcdefghijk", "dsadsa")) //输出-1 + +}