1409 查询带键的排列

在这里插入图片描述

  1. 模拟:
    每一次查询和移动都要花费O(M)的时间,共查询Q次。时间复杂度为O(Q*M),空间复杂度为O(M)。
class Solution:
    def processQueries(self, queries: List[int], m: int) -> List[int]:
        ans = []
        p = [i+1 for i in range(m)]
        for x in queries:
            pos = p.index(x)
            ans.append(pos)
            p = [p[pos]]+p[:pos]+p[pos+1:]
        return ans
  1. 树状数组:
    首先可以在数组p前空出q个位置,这样题中的“把元素挪至起始位置”只要从位置q-1开始倒着插入就好,在逻辑上维护这样一个数组,实际上只要用一个数组记录p中每个元素在这个逻辑数组中的位置。
    在p中找到一个元素的位置,相当于计算这个元素之前有多少个元素。
class Solution:
    @staticmethod
    def lowbit(x):
        return (-x) & x

    def update(self, index, x, tree):
        while index < len(tree):
            tree[index] += x
            index += self.lowbit(index)

    def query(self, index, tree):
        ans = 0
        while index >= 1:
            ans += tree[index]
            index -= self.lowbit(index)
        return ans

    def processQueries(self, queries, m: int):
        ans = []
        p = [0]+[len(queries) +1+ i for i in range(m)]
        t = [0] * (len(queries) + 1) + [1] * m
        tree = [0] * len(t)

        for i in range(1, len(t)):
            self.update(i, t[i], tree)

        j = len(queries)
        for x in queries:
            pos = p[x]
            p[x] = j
            ans.append(self.query(pos - 1, tree))
            self.update(pos, -1, tree)
            self.update(j, 1, tree)
            j -= 1

        return ans


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值