您的位置:首页 > 职场人生

程序员面试金典2.1:编写代码,移除未排序的链表中的重复节点

2015-08-30 10:22 519 查看
2.1编写代码,移除未排序的链表中的重复节点

解法一:如果不得使用临时缓冲区,该怎么解决?

要想移除链表中的重复节点,我们需要设法记录有哪些是重复的。这里只需要使用到一个简单的散列表。

在下面的解法中,我们会直接迭代访问整个链表,将每个节点加入到散列表。若发现有重复的元素,将该节点从链表中移除,然后继续迭代。这个题目使用了链表,因此只需要扫描一次就能搞定。

/**
*
*/
package project02;

import java.util.Hashtable;

import util.LinkedListNode;

/**
* @author JInShuangQi
*
* 2015年8月30日
*/
public class E01DeleteDupsNumber {
private LinkedListNode<Integer> head;
private LinkedListNode<Integer> tail;
private int size;

// 尾部插入
public boolean addTail(int data) {
if (this.head == null) {
this.head = new LinkedListNode<Integer>(null, data, null);
this.tail = this.head;
} else {
LinkedListNode<Integer> newnode = new LinkedListNode<Integer>(this.tail, data, null);
this.tail.next = newnode;
this.tail = newnode;
}
this.size++;

return true;
}
public String toString() {
if (this.isEmpty())
return "[]";
else {
StringBuffer st = new StringBuffer("[");
for (LinkedListNode<Integer> curent = this.head; curent != null; curent = curent.next)
st.append(curent.data.toString() + " ,");
st.append("]");
return st.toString();
}
}
public boolean isEmpty() {
return this.size == 0;
}

public void deleteDups(LinkedListNode<Integer> n){
Hashtable<Integer, Boolean> table = new Hashtable<Integer, Boolean>();
LinkedListNode<Integer> previous = null;
while(n != null){
if(table.containsKey(n.data)){
previous.next = n.next;
}else{
table.put(n.data, true);
previous = n;
}
n =n.next;
}
while(head!=null){
System.out.println(head.data.toString());
head= head.next;
}
}
public void deleteDups2(LinkedListNode<Integer> head){
if(head == null)
return;
LinkedListNode<Integer> current = head;
while(current != null){
//移除后续值相同的所有节点
LinkedListNode<Integer> runner = current;
while(runner.next != null){
if(runner.next.data == current.data){
runner.next = runner.next.next;
}else{
runner = runner.next;
}
}
current= current.next;
}
while(head!=null){
System.out.println(head.data.toString());
head= head.next;
}
}
public static void main(String[] args){

E01DeleteDupsNumber test = new E01DeleteDupsNumber();
test.addTail(1);
test.addTail(2);
test.addTail(3);
test.addTail(3);
test.addTail(4);
test.addTail(1);

test.deleteDups2(test.head);

}
}
上述代码含有测试用例,deleteDups()的时间复杂度为O(N),其中N为链表节点数目。

解法二:不使用缓冲区

如不借助额外的缓冲区,可以用两个指针来迭代:current迭代访问整个链表,runner用于检查后续的节点是否重复

上述代码中的deleteDups2()

该代码的空间复杂度为O(1),时间复杂度为O(N2)
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: