2009年计算机考研题解——综合第2题

 

题目:
   42.(15分)

    已知一个带有表头结点的单链表,结点结构为:

    假设该链表只给出了头指针list,在不改变链表的前提下,请设计一个尽可能高效的算法,查找链表中倒数第K个位置上的结点 (K为正整数),若查找成功,算法输出该结点的data域的值,并返回1;否则只返回0。要求:

    (1)描述算法的基本设计思想;

    (2)描述算法的详细实现步骤(使用C或 C++或 Java语言实现),关键之处请给出简要注释。
答案:
增加2个指针变量和一个整型变量,从链表头向后遍历,其中指针p指向当前遍历的结点,指针p1指向p1所指向结点的前k个结点,如果p之前没有k个结点,那么p1指向表头结点。用整型变量i表示当前遍历了多少个结点,当i>k时,p1随着每次的遍历,也向请移动一个结点。则遍历完成时,p1或者指向表头结点,或者指向链表中倒数第k个位置上的结点。


算法1:空间3,时间n
p=list->link;
p1=list;
i=1;
while(p)
{
    p=p->link;
    i++;
    if (i> k) p1=p1->next;
}
if (p1==list) return 0;
else
{
    printf("%d/n", p1->data);
    return 1;
}

还有其他算法如下:
算法2:空间3,时间n

p=list->link;
p1=list;
i=1;
while(p&&i<k)
{
    p=p->link;
    i++;
}
if (!p) return 0;
while(p)
{
    p=p->link;
    p1=p1->next;
}
printf("%d/n", p1->data);
return 1;

算法3:
首先遍历整个链表,获取链表的长度n。
再重新遍历到链表的第n-k+1个结点,即为所求
空间:2,时间2n
p=list->link;
i=0;
while(p)
{
    p=p->link;
    i++;
}
if (i<k) return 0;
p=list->link
while(i>k)
{
    p=p->link;
    i--;
}
printf("%d/n", p1->data);
return 1;

比较:空间复杂度:算法3最好。
时间复制度:算法2最好

你可能感兴趣的:(java,c,算法,list,语言)