Python 从数组中删除重复项并保持顺序-O(n)time并返回相同的引用
在线搜索没有帮助。我甚至不确定这是否可能 最好用Python编写解决方案,但一切都可以 ===== 编辑:我最初说的是O(1)空格,但我认为这是不可能的 更改要求:Python 从数组中删除重复项并保持顺序-O(n)time并返回相同的引用,python,algorithm,Python,Algorithm,在线搜索没有帮助。我甚至不确定这是否可能 最好用Python编写解决方案,但一切都可以 ===== 编辑:我最初说的是O(1)空格,但我认为这是不可能的 更改要求: 没有空间要求,但您必须就地修改输入并返回。我认为在O(n)时间和O(1)空间中不可能做到这一点。要获得O(n)时间,你必须有一个草稿行(带有O(1)插入和查找,例如a)记录你已经看到的所有元素;这需要O(m)空间(其中m是唯一元素的数量)。相反,要获得O(1)空间,必须为每个元素重新扫描数组中较早的元素,即O(n2)时间 ['a',
没有空间要求,但您必须就地修改输入并返回。我认为在O(n)时间和O(1)空间中不可能做到这一点。要获得O(n)时间,你必须有一个草稿行(带有O(1)插入和查找,例如a)记录你已经看到的所有元素;这需要O(m)空间(其中m是唯一元素的数量)。相反,要获得O(1)空间,必须为每个元素重新扫描数组中较早的元素,即O(n2)时间
['a', 'c','a','b','b'] -> ['a', 'c', 'b']
如果您接受O(m)草稿行,这将满足“就地修改阵列”要求,并在O(n)时间内运行
我在这些函数中进行手动数组索引,因为使用任何常用的for..in构造从正在迭代的数组中删除元素是不安全的。您可以在第一个循环中使用for..in循环,但会丢失,因此可读性较差
如果您以前没有看到过,则仅当循环未通过
中断退出时才会执行。要保持速度效率,您需要使用O(n)空间来记录已存在的记录。如果有大量的副本,则不会占用太多空间。但是,标准数组上的del操作是O(n),因为它必须移动以下所有元素
def remove_duplicates_quadratic(arr):
"""Remove all duplicated elements from ARR in O(1) space and O(n²) time.
ARR is modified in place and is not returned (like `sort`)."""
n = len(arr)
i = 0
while i < n:
for j in range(i):
if arr[j] == arr[i]:
del arr[i]
n -= 1
break
else:
i += 1
def uniquify(数据):
used=set()
i=0
而i
这个怎么样?我认为时间复杂度和空间复杂度都是O(n)
O(n)时间,O(n)空间
def unique(arr):
index = 0
s = set()
for i in range(len(arr)):
if arr[i] not in s:
arr[index] = arr[i]
index += 1
s.add(arr[i])
arr[index:] = []
O(n^2)时间,O(1)空间
它当然是以n^2为界的,但实际上它的边界更小
for index, item in enumerate(myListCopy):
if item not in uniqueList: uniqueList.append(item)
else: myList.pop(index)
你得让我们看看你的尝试。Stackoverflow不仅仅是一个你把你的问题放入其中并给出答案的函数,这是不可能的。在O(n)空间中是可行的。如果数组/数据被排序,我认为这是可以做到的。(就像地图减少字数中的减少步骤)@viper是的,减少或累积调用可以使用排序。@AidanGomez:欢迎链接到相关材料,但这显然不是dup。我认为它确实保持了顺序,但O(n)空间。@JoranBeasley:O(1)空间可以使用就地算法。虽然…oset
不在标准库中,但可以满足时间要求,请提供PyPI或其他任何地方的链接。我不得不花了很长一段时间来了解这一点,以说服我自己它可以按预期工作。。。。也就是说+1,因为它满足O(1)空间的要求…我认为到目前为止,这实际上是唯一满足OP要求的解决方案..看起来适合O(1)空间。很抱歉,我最初对O(1)空间和O(n)时间提出了不可能的要求。我之所以选择,是因为他的最后一行arr[index:][]
看起来更简洁,我认为现在是O(1)时间,而你的del-arr[j:I]
是O(I-j)。无论如何+1。del-arr[j:i]
在这种情况下应该是O(1),但我还没有真正阅读我链接到的代码,以确定这是否正确。del
是O(n)操作,所以你的算法是O(n^2)总计。太糟糕了,Python没有内置的链接列表(我可以找到),但函数依赖于输入,因此已经超出了它的控制范围。没关系,链表会扰乱索引速度。看起来这既满足了I/O要求,也满足了要求。也很简单。
def remove_duplicates_quadratic(arr):
"""Remove all duplicated elements from ARR in O(1) space and O(n²) time.
ARR is modified in place and is not returned (like `sort`)."""
n = len(arr)
i = 0
while i < n:
for j in range(i):
if arr[j] == arr[i]:
del arr[i]
n -= 1
break
else:
i += 1
def uniquify(data):
used = set()
i = 0
while i < len(data):
if data[i] in used:
del data[i] # or data.pop(i)
else:
used.add(data[i])
i += 1
return data # not strictly necessary because array is modified in-place
def unique(arr):
index = 0
s = set()
for i in range(len(arr)):
if arr[i] not in s:
arr[index] = arr[i]
index += 1
s.add(arr[i])
arr[index:] = []
uniqueList = []
index = 0
while index < len(myList):
item = myList[index]
if item not in uniqueList: uniqueList.append(item)
else: myList.pop(index)
index += 1
for index, item in enumerate(myListCopy):
if item not in uniqueList: uniqueList.append(item)
else: myList.pop(index)
index = 0
while index < len(myList):
subIndex = index + 1
while subIndex < len(myList):
if myList[subIndex] == myList[index]: myList.pop(subIndex)
subIndex += 1
index += 1
for item in myList:
if myList.count(item) > 1: myList.remove(item)
lst1= ['a', 'c','a','b','b'] #-> ['a', 'c', 'b']
lst2 = []
for l in lst1:
if l not in lst2:
lst2.append(l)
print lst2