筆者由于在找工作,所以近期最主要的任務就是準備面試舞箍,不打無準備之仗靠汁。只有你準備充分了蜂大,那么你想要的機會才有機會入你懷中。
筆者會將準備面試的學習過程記錄下來蝶怔,方便自己復盤的同時也希望能給一道找工作的小伙伴們一些幫助奶浦。筆者準備的內(nèi)容大綱如下
Android面試大綱.png
下面是本篇博客的正菜部分:
倒數(shù)第K個節(jié)點
在一個單鏈表中找到倒數(shù)第k個節(jié)點
很容易想到先遍歷一次鏈表節(jié)點個數(shù)n,第二次遍歷只需要找第n-k+1個節(jié)點踢星。
當你說出這個想法的時候澳叉,面試官肯定會提示你他期待的答案是只允許遍歷一次鏈表
關鍵點:是否可以想到使用兩個指針,移動過程中兩個所在位置始終相差k-1的距離斩狱。當前一個指針移到尾部時耳高,后一個指針正好指向倒數(shù)第k個結點。
public ListNode findKthTail(ListNode pHead, int k){
if(pHead == null || k<=0) return null;
ListNode pAHead = pHead;
ListNode pBehind = null;
//使前面的指針快與后面的節(jié)點k-1個節(jié)點位
for(int i=0;i<k-1;i++){
if(pAHead.next != null){ //容易忽視隱藏的邊界條件所踊,有可能k的值大于節(jié)點數(shù)
pAHead = pAHead.next;
}else{
return null;
}
}
//讓兩個指針始終保持k-1個節(jié)點位泌枪,等前面的節(jié)點到尾節(jié)點時,后一個節(jié)點到達倒數(shù)第k個節(jié)點
pBehind = pHead;
while(pAHead.next != null){
pAHead = pAHead.next;
pBehind = pBehind.next;
}
return pBehind;
}
引申:如果讓一次遍歷找鏈表的中間結點可以使用類似的方法秕岛。只需要在指針移動時碌燕,前一個指針一次移動兩個節(jié)點误证,后一個指針一次移動一個節(jié)點。前一個指針到達尾部時修壕,后一個指針到達中間節(jié)點愈捅。
反轉鏈表
反轉一個單鏈表,返回它的頭節(jié)點慈鸠。
很容易想到的是直接反轉蓝谨,后一個節(jié)點指向前一個節(jié)點。但是會有一個問題青团,到為尾節(jié)點的時候譬巫,會發(fā)生鏈表中斷,這是因為尾節(jié)點的下一個結點為空督笆。
關鍵點:要將前一個節(jié)點保存下來芦昔,所以要使用三個指針
public ListNode reverseListNode(ListNode pHead){
if(pHead ==null) return null;
ListNode pNewHead = null;
ListNode pPre = null;
ListNode pCur = pHead;
while(pCur !=null){
ListNode pNext = pCur.next;
if(pNext == null){ //找到新的頭節(jié)點
pNewHead = pCur;
}
pCur.next = pPre; //反轉
pPre = pCur;
pCur = pNext;
}
return pNewHead;
}
是否可以想到添加一個指針來保存之前的節(jié)點是解題的關鍵