这道题目考查的是字符串处理能力,尤其是如何在一组字符串中寻找最长公共前缀。解决这个问题的关键在于比较每个字符串的对应位置的字符,直到在某个位置上找到不匹配的字符为止。这个问题可以通过多种方法解决,下面是几种常见的解题思路:
1. 水平扫描法
这种方法逐个遍历字符串数组中的每个字符串,对于每个字符串,更新最长公共前缀。
- 开始时,假设第一个字符串是最长公共前缀。
- 然后逐个与后续的字符串比较,每次比较后,更新最长公共前缀。
- 如果在某次更新后最长公共前缀为空,说明没有公共前缀,可以直接返回空字符串。
- 这个过程一直持续到比较完所有字符串。
func longestCommonPrefix(strs []string) string {
length := len(strs)
if length < 1 {
return ""
}
prefix := strs[0]
for i := 1; i < len(strs); i++ {
//i跟i+1比较
prefix = samePrefix(prefix, strs[i])
}
return prefix
}
//取两个字符串的公共前缀
func samePrefix(s1 string, s2 string) string {
minLen := len(s1)
if minLen > len(s2) {
minLen = len(s2)
}
var sameLen int
for i := 0; i < minLen; i++ {
if s1[i] == s2[i] {
sameLen++
} else {
break
}
}
return s1[:sameLen]
}
2. 垂直扫描法
这种方法从所有字符串的第一个字符开始比较,然后是所有字符串的第二个字符,依此类推。
- 比较同一位置上的字符是否相同。
- 如果在某个位置上字符不全相同,或者某个字符串已经结束,那么到达的位置就是最长公共前缀的长度。
func longestCommonPrefix(strs []string) string {
length := len(strs)
if length < 1 {
return ""
}
if strs[0] == "" {
return ""
}
prefix := ""
//找到长度最短的
minLen := minLen(strs)
for i := 0; i < minLen; i++ {
c := strs[0][i]
for _, str := range strs {
//不应该strings.HasPrefix来比,应该按位比,否则会增加复杂度
if str[i] != c {
return prefix
}
}
//将c加入前缀
prefix += string(c)
}
return prefix
}
func minLen(strs []string) int {
minLen := len(strs[0])
for _, str := range strs[1:] {
if len(str) < minLen {
minLen = len(str)
}
}
return minLen
}
3. 分治法
这种方法将原问题分解为更小的问题,然后将小问题的答案组合起来解决原问题。
- 将字符串数组分成两部分,分别求出左半部分和右半部分的最长公共前缀,然后找出这两个前缀的公共前缀。
从两个字符串求公共前缀,推演到多个字符串求公共前缀
func longestCommonPrefix(strs []string) string {
if len(strs) < 1 {
return ""
}
return getPrefix(strs, 0, len(strs)-1)
}
func getPrefix(strs []string, left, right int) string {
if right <= left {
return strs[left]
}
leftPrefix := getPrefix(strs, left, left+(right-left)/2)
rightPrefix := getPrefix(strs, left+(right-left)/2+1, right)
return samePrefix(leftPrefix, rightPrefix)
}
//取两个字符串的公共前缀
func samePrefix(s1 string, s2 string) string {
minLen := len(s1)
if minLen > len(s2) {
minLen = len(s2)
}
var sameLen int
for i := 0; i < minLen; i++ {
if s1[i] == s2[i] {
sameLen++
} else {
break
}
}
return s1[:sameLen]
}
4. 二分查找法
这种方法利用二分查找确定最长公共前缀的最大可能长度。
- 首先,找出所有字符串中长度最短的那个,并将其长度作为二分查找的上界。
- 然后通过二分查找,在这个长度范围内寻找最长公共前缀。
- 每次二分查找时,检查所有字符串的前mid(left和right的中间值)个字符是否相同,根据检查结果调整搜索范围。