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

《剑指Offer》学习笔记--面试题16:反转链表

2015-05-08 13:24 197 查看
题目:定义一个函数,输入一个链表的头结点,反转该链表并输出反转后链表的头结点。

链表结点定义如下:

struct ListNode
{
int     m_nKey;
ListNode* m_pNext;
};
解决与链表相关的问题总是有大量的指针操作,而指针操作的代码总是容易出错的。在实际的软件开发周期中,设计的时间通常不会比编码的时间短。在面试的时候我们不要急于动手写代码,而是一开始仔细分析和设计,这将会给面试官留下很好的印象。与其很快地写出一个漏洞百出的代码,不如仔细分析再写出鲁棒的代码。

为了正确地反转一个链表,需要调整链表中指针的方向。为了将调整指针这个复杂的过程分析清楚,我们可以借助图形来直观地分析。

代码如下:

ListNode *ReverseList(ListNode* pHead)
{
ListNode *pReversedHead = NULL;
ListNode *pNode = pHead;
ListNode *pPrev = NULL;
while(pNode != NULL){
ListNode *pNext = pNode->m_pNext;

if(pNext == NULL)
pReversedHead = pNode;
pNode->m_pNext = pPrev;

pPrev = pNode;
pNode = pNext;
}

return pReversedHead;
}
一般应聘者经常出现如下3中问题:

(1)输入的链表头指针为NULL或者整个链表只有一个结点时,程序立即崩溃。

(2)反转后链表出现断裂。

(3)返回的反转之后的头结点不是原始链表的尾结点。

那么如何才能及时发现并纠正代码中的问题,以确保不犯上述错误呢?一个很好的办法就是提前想好测试用例。在写出代码之后,立即用实现准备好的测试用例检查测试。如果面试是以手写代码的方式,那也要在心里默默地运行代码做单元测试。只有确保代码通过测试之后再提交面试官。我们要记住一点:自己多花时间找出问题并修正问题,比在面试官找出问题之后再去慌慌张张修改代码要好得多。

以这道题为例,我们至少应该想到几类测试用例的测试:

(1)输入的链表头指针是NULL。

(2)输入的链表只有一个结点。

(3)输入的链表有多个结点。

如果我们确信代码能够通过这3类测试用例的测试,那我们就有很大的把握能够通过这轮面试了。

本题扩展:

用递归实现同样的反转链表的功能。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: