惊!! Go里面居然还有这个方法,题解这么直观秀到我了

Posted 了 凡

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了惊!! Go里面居然还有这个方法,题解这么直观秀到我了相关的知识,希望对你有一定的参考价值。

博主介绍:

我是了凡,昵称的意义是希望本人任何时候以善良为先,以人品为重,喜欢了凡四训中的立命之学、改过之法、积善之方、谦德之效四训,更喜欢每日在简书上投稿日更的读书感悟笔名:三月_刘超。专注于 Go Web 后端,辅学Python、Java、算法、前端等领域。微信公众号【了凡银河系】期待你的关注,企鹅群号(798829931)。未来大家一起加油啊~


背景

LeetCode一道中等题目

题目

L32题 在排序数组中查找元素的第一个和最后一个位置

给定一个按照升序排列的整数数组 nums,和一个目标值 target。找出给定目标值在数组中的开始位置和结束位置。
如果数组中不存在目标值 target,返回 [-1, -1]。
进阶:
	你可以设计并实现时间复杂度为 O(log n) 的算法解决此问题吗?

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/find-first-and-last-position-of-element-in-sorted-array
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。



原思路

思路:
双指针 两头指针一次只挪动一边

题解:

func searchRange(nums []int, target int) []int {
	result := []int{-1, -1}
	if len(nums) == 0 {
		return result
	}
	j := len(nums) - 1
	i1 := true
	j1 := true
	for i := 0; i != j && (i1 != false || j1 != false); {

		if nums[i] == target && i1 {
			result[0] = i
			i1 = false
		}else if i1 {
			i ++
		}

		if i == j {
			break
		}

		if nums[j] == target && j1 {
			result[1] = j
			j1 = false
		}else if j1 {
			j --
		}
	}
	return result
}

结果


可以看到没能通过按照这个思路应该是可以通过的,只是可能需要在想一下
这个题要求是用二分查找解决的,显然不合题意,而且没能通过

参考后

之后二分还没有想,先看了下题解看到了一个方法 SearchInts

SearchInts方法

官方注释:

// SearchInts searches for x in a sorted slice of ints and returns the index
// as specified by Search. The return value is the index to insert x if x is
// not present (it could be len(a)).
// The slice must be sorted in ascending order.

意思就是

在一个整数排序的切片中搜索x,并返回索引
由Search指定。返回值是插入x的索引(如果x是)
不存在(它可能是len(a))。
切片必须按升序排序。

可以看到正好是升序满足题意,并且找到返回索引,否则返回 len(数组a)

由此题解可为

func searchRange(nums []int, target int) []int {
	leftmost := sort.SearchInts(nums, target)
	if leftmost == len(nums) || nums[leftmost] != target {
		return []int{-1, -1}
	}
	rightmost := sort.SearchInts(nums, target + 1) - 1
	return []int{leftmost, rightmost}
}

结果


可以看到成功通过,但是没有符合题意,所以由下可解

题解

func searchRange(nums []int, target int) []int {
    n := len(nums)
    left := 0
    right := n-1
    for left <= right{ //二分法查找
        m := (left + right)/2
        if nums[m] == target{
            i := m
            j := m
            for (i>=0 && nums[i] == target) || (j<=n-1 &&nums[j] == target){ //左右指针扩散
                if i>=0 && nums[i] == target{
                    i--
                }
                if j<=n-1 && nums[j] == target{
                    j++
                }
            }
            return []int{i+1 ,j-1}
        }
        if nums[m] > target{
            right = m-1
        }else{
            left = m+1
        }
    }
    return []int{-1,-1}
}

结果


这次就先讲到这里,如果想要了解更多的golang语言内容一键三连后序每周持续更新!

以上是关于惊!! Go里面居然还有这个方法,题解这么直观秀到我了的主要内容,如果未能解决你的问题,请参考以下文章

惊:FastThreadLocal吞吐量居然是ThreadLocal的3倍!!!

Git 居然还有这么高级用法

除阿里网易和字节外,杭州居然还有这么多互联网公司!

2.3.5Google Analytics高级应用——热力图

iPhone里的safari居然还有一个这么强大的功能!你发现了吗?

秀到飞起!Alibaba全新出品JDK源码学习指南(终极版)限时开源