📌  相关文章
📜  给定数组中存在于索引[L,R]范围内的Count 1(1)

📅  最后修改于: 2023-12-03 15:11:40.305000             🧑  作者: Mango

给定数组中存在于索引[L,R]范围内的Count 1

给定一个包含0和1的数组,要求在索引[L,R]范围内找到1的个数。

解法一:暴力求解

我们可以通过遍历[L,R]中的每一个元素,统计1的个数来求解。具体实现如下:

def count_ones(arr, L, R):
    count = 0
    for i in range(L, R+1):
        if arr[i] == 1:
            count += 1
    return count

时间复杂度为O(R-L+1),空间复杂度为O(1)。

解法二:前缀和

我们可以先计算出arr数组的前缀和数组prefix,其中prefix[i]表示arr数组中前i个元素中1的个数。那么[L,R]范围内的1的个数就可以通过prefix[R]-prefix[L-1]来计算。具体实现如下:

def get_prefix_sum(arr):
    n = len(arr)
    prefix = [0]*n
    prefix[0] = arr[0]
    for i in range(1, n):
        prefix[i] = prefix[i-1] + arr[i]
    return prefix

def count_ones(arr, L, R):
    prefix = get_prefix_sum(arr)
    return prefix[R] - prefix[L-1] if L>0 else prefix[R]

时间复杂度为O(n),空间复杂度为O(n)。

解法三:线段树

线段树是一种常用的数据结构,可以用来高效地处理数组区间操作。我们可以通过构建线段树,将原始数组arr转化为区间1的个数,然后用线段树来处理[L,R]范围内的query操作。具体实现如下:

class SegmentTree():
    def __init__(self, n, arr):
        self.tree = [0]*(4*n)
        self.build_tree(arr, 0, 0, n-1)

    def build_tree(self, arr, node, start, end):
        if start == end:
            self.tree[node] = arr[start]
        else:
            mid = (start+end)//2
            self.build_tree(arr, 2*node+1, start, mid)
            self.build_tree(arr, 2*node+2, mid+1, end)
            self.tree[node] = self.tree[2*node+1] + self.tree[2*node+2]

    def query(self, node, start, end, L, R):
        if R<start or L>end:
            return 0
        elif L<=start and R>=end:
            return self.tree[node]
        else:
            mid = (start+end)//2
            left = self.query(2*node+1, start, mid, L, R)
            right = self.query(2*node+2, mid+1, end, L, R)
            return left + right

def count_ones(arr, L, R):
    n = len(arr)
    tree = SegmentTree(n, arr)
    return tree.query(0, 0, n-1, L, R)

时间复杂度为O(logn),空间复杂度为O(n)。

综上所述,对于给定数组中存在于索引[L,R]范围内的Count 1的问题,我们可以采用暴力求解、前缀和和线段树等不同的算法进行求解,根据实际情况选择合适的算法来解决该问题。