我已经看过,编写并测试了一些逻辑以删除链表中的重复项。例如使用两个循环(O(n2))
,或者排序和删除重复项虽然不能保留顺序
我只是想知道,如果我们提取链表的元素并开始创建二进制搜索树,使用二叉树算法中的标准重复检测来检测重复项,那么它是有效还是清晰。
这会比现有逻辑更有效,还是更糟?
答案 0 :(得分:2)
您可以在O(n)
时间内使用O(n)
额外内存。这比BST方法更好:
答案 1 :(得分:1)
您的Binary Search tree(BST)替代方案会更快。让我们做一些分析:
O(1)
N * O(log(N))
中的每个节点填充BST
注意,作为插入操作的一部分,重复项将不添加到树中。O(N)
删除重复项的BST方法在O(1)+O(N)+O(N*log(N)) =
O(N*log(N))
它需要运行更多代码和更多内存,但会删除quasi-linear time中的重复项。
答案 2 :(得分:0)
最好的选项(fastern)是创建二叉树来查找副本,但是你需要更多的内存和代码。
在c#中你有字典,在c ++中我认为你可以使用任何模板库
答案 3 :(得分:0)
这个解决方案解决了不允许额外内存并更改链接列表的问题。解决方案是在C#
public static void removeDuplicates(Node root) {
Node reset = root;
Node current = null;
Node previous = null;
Hashtable h = new Hashtable();
//initialize hash table to all 0 values
while (root != null)
{
if(!h.ContainsKey(root.value))
h.Add(root.value, 0);
root = root.next;
}
root = reset;
///count the number of times an element appears
while (root != null)
{
h[root.value] = int.Parse(h[root.value].ToString()) + 1;
root = root.next;
}
root = reset;
previous = root;
current = previous.next;
while (current != null) {
if (int.Parse(h[current.value].ToString())>1)
{
h[current.value] = int.Parse(h[current.value].ToString())-1;
previous.next = current.next;
current = current.next;
}
else {
previous = previous.next;
current = current.next;
}
}
// print them for visibility purposes
while (reset != null) {
Console.Write(reset.value + "->");
reset = reset.next;
}
}
static void Main(string[] args)
{
Node one = new Node(1);
Node two = new Node(1);
Node three = new Node(1);
Node four = new Node(2);
Node five = new Node(2);
RemoveDuplicates(one);
}