剑指offer 链表
来源:互联网 发布:windows 8系统安装 编辑:程序博客网 时间:2024/04/30 02:14
单向链表
遍历
1.1 题目(面试题5):从尾到头打印链表
解法一:借助栈;
import java.util.ArrayList; import java.util.Stack; public class Solution { public ArrayList<Integer> printListFromTailToHead(ListNode listNode) { ArrayList<Integer> array=new ArrayList<Integer>(); if(listNode==null) return array; Stack<Integer> stack=new Stack<Integer>(); ListNode temp=listNode; while(temp!=null){ stack.push(temp.val); temp=temp.next; } while(!stack.isEmpty()){ array.add(stack.pop()); } return array; } }
解法二:递归的实现;
import java.util.ArrayList; import java.util.Stack; public class Solution { public ArrayList<Integer> printListFromTailToHead(ListNode listNode) { ArrayList<Integer> array=new ArrayList<Integer>(); if(listNode==null) return array; if(listNode.next!=null){ array.addAll(printListFromTailToHead(listNode.next)); } array.add(listNode.val); return array; } }
解法三:改变链表的指针指向(得修改输入的数据);
1.2 题目(面试题13):在O(1)时间删除链表结点
解法一:从头到尾遍历查找,O(n)的时间复杂度;
解法二:把要删除结点的下一个结点(充分利用结点信息)复制到当前结点,然后删除下一结点,时间复杂度(O(n-1)*O(1)+O(n))/n(注意要考虑尾结点的情况);
1.3 题目(面试题57):删除链表中重复的结点
import java.util.ArrayList; public class Solution { public ListNode deleteDuplication(ListNode pHead) { if(pHead==null || pHead.next==null) return pHead; ListNode temp=pHead; ListNode preNode=new ListNode(0); preNode.next=pHead; pHead=preNode; boolean flag=false; //因为删除操作和非删除不一样,所以需要标记一下 while(temp!=null){ while(temp.next!=null && temp.val==temp.next.val){ //这个循环是关键,直到找到 temp=temp.next; flag=true; } if(flag){ preNode.next=temp.next; temp=temp.next; flag=false; } else{ preNode=preNode.next; temp=temp.next; } } return pHead.next; } }
反转
2.1 题目(面试题16):反转链表
解法一:头插法,有助于理解java中的HashMap
public class Solution { public ListNode ReverseList(ListNode head) { if(head==null || head.next==null) return head; ListNode nHead=new ListNode(0); while(head!=null){ ListNode temp=head; head=head.next; ② temp.next=nHead.next; nHead.next=temp; } return nHead.next; } }解法二:递归法
public class Solution { public ListNode ReverseList(ListNode head) { if(head==null || head.next==null) return head; ListNode nHead=ReverseList(head.next); head.next.next=head; head.next=null; return nHead; } }
插入
3.1 题目(面试题17):合并两个有序的链表
public class Solution { public ListNode Merge(ListNode list1,ListNode list2) { if(list1==null) return list2; else if(list2==null) return list1; ListNode mergeHead=null; if(list1.val>=list2.val){ mergeHead=new ListNode(list2.val); mergeHead.next=Merge(list1,list2.next); }else{ temp=new ListNode(list1.val); temp.next=Merge(list1.next,list2); } return mergeHead; } }
查找
4.1 题目(面试题37):两个链表的第一个公共结点
解法一:暴力搜索法;
解法二:见从尾到头遍历链表的辅助栈法;
解法三:快慢指针;
4.2 题目(面试题15):链表中的倒数第K个结点
解法一:遍历两次链表的解法,或者见从尾到头打印链表;
public class Solution { public ListNode FindKthToTail(ListNode head,int k) { if(head==null) return null; int count=0; ListNode node=head; while(node!=null){ count++; node=node.next; } if(k>count) return null; node=head; int num=0; while(node!=null){ num++; if(num==(count-k+1)){ break; } node=node.next; } return node; } }
解法二:遍历一次的解法,即快慢指针的解法;
public class Solution { public ListNode FindKthToTail(ListNode head,int k) { if(head==null || k==0) return null; ListNode n1=head; ListNode n2=head; int count=0; while(n1!=null){ if(count>=k){ n2=n2.next; } count++; n1=n1.next; } if(count<k) return null; return n2; } }
循环链表
5.1 题目(面试题56):链表中环的入口结点
解法一:先判断是不是有环,再计算环中结点的个数,再利用快慢指针找到环的入口结点,一个题当成三道题。
5.2 题目(面试题45):圆圈中最后剩下的数字,即约瑟夫环问题
解法一:借助循环链表;
解法二:数学规律;
5.3 循环缓存
复杂链表
6.1 题目(面试题26):复杂链表的复制
6.2 题目(面试题27):二叉搜索树与双向链表
0 0
- 剑指offer 链表
- 剑指offer-链表
- (剑指offer)链表
- 剑指offer --链表
- 剑指offer 链表
- 剑指Offer Java版 链表
- [剑指offer]算法3 链表
- 剑指OFFER
- 剑指offer
- 剑指Offer
- 剑指offer
- 剑指Offer
- 剑指offer
- 剑指offer
- 剑指offer
- 剑指Offer
- 剑指offer
- 剑指offer
- hdu 5456 Matches Puzzle Game(dp)
- Servlet响应
- ubuntu 输入密码后黑屏
- 使用SigerProgress快速构建进度组件
- PL/SQL Developer连接本地Oracle 11g 64位数据库
- 剑指offer 链表
- nginx配置简单的反向代理
- [导航]图像相关
- JavaWeb-会话
- linux地址空间学习--未完待续
- 堆排序
- PHP安装gpg扩展
- JavaWeb-过滤器
- hdoj4833Best Financing【dp】