Lintcode 搜索插入位置/搜索旋转排序数组插入位置

问题1 搜索插入位置
给定一个排序数组和一个目标值,如果在数组中找到目标值则返回索引。如果没有,返回到它将会被按顺序插入的位置。

你可以假设在数组中无重复元素。

样例
[1,3,5,6],5 → 2

[1,3,5,6],2 → 1

[1,3,5,6], 7 → 4

[1,3,5,6],0 → 0

挑战
O(log(n)) time

def searchInsert(self, A, target):
        # write your code here
        n=len(A)
        if(n==0):
            return 0
        left,right=0,n-1
        while(right>left and (right-left)!=1):
            mid=left+((right-left)>>1)
            if(A[mid]>target):
                right=mid
            elif(A[mid]<target):
                left=mid
            else:
                return mid
        if(target<=A[left]):
            return left
        elif(A[right]<target):
            return right+1

        else:
            return right

思路:
要求O(log(n)) time,显示是二分法求解,一步步找出target在数组中的位置,当只剩下left和right两个元素时候,比较他们与target的关系,即可以找到要插入的位置。

问题2 搜索旋转排序数组
假设有一个排序的按未知的旋转轴旋转的数组(比如,0 1 2 4 5 6 7 可能成为4 5 6 7 0 1 2)。给定一个目标值进行搜索,如果在数组中找到目标值返回数组中的索引位置,否则返回-1。

你可以假设数组中不存在重复的元素。

样例
给出[4, 5, 1, 2, 3]和target=1,返回 2

给出[4, 5, 1, 2, 3]和target=0,返回 -1

挑战
O(logN) time

def searchInsert(self, A, target):
        # write your code here
        n=len(A)
        if(n==0):
            return 0
        left,right=0,n-1
        while((right-left)>1):
            mid=left+((right-left)>>1)
            if(A[mid]>target):
                right=mid
            elif(A[mid]<target):
                left=mid
            else:
                return mid
        if(target==A[left]):
            return left
        elif(A[right]==target):
            return right
        else:
            return -1
    def search(self, A, target):
        # write your code here
        n=len(A)
        if n==0:
            return -1
        location=-1
        for i in range(n-1):
            if(A[i+1]-A[i]<0):
                location=i
        if location==-1:
            return Solution.searchInsert(self=self,A=A,target=target)
        else:
            arrRight=A[(location+1):]
            arrLeft=A[:(location+1)]
            print('loc',location)
            if(target<=A[n-1]):
                indRight=Solution.searchInsert(self=self,A=arrRight,target=target)
                print('indRight',indRight)

                return location+1+indRight if indRight!=-1 else -1

            elif(target>=A[0]):
                indLeft=Solution.searchInsert(self=self,A=arrLeft,target=target)
                print('indLeft',indLeft)
                return indLeft if indLeft!=-1 else -1
            else:
                return -1

思路:
与之前的问题有一点不同的是,这里如果数组中不存在target则返回-1;
先找旋转数组中的boundary(也要考虑到这个数组没有boundary,就是一个顺序数组的情况)。
找到boundary之后,将数组分成两个小数组,然后分别应用搜索插入位置的算法即可。对于右边数组,在得到插入位置之后,还需要加一个boundary大小。

猜你喜欢

转载自blog.csdn.net/Bismarckczy/article/details/82605253
今日推荐