zoukankan      html  css  js  c++  java
  • 13--输出链表中倒数第k个节点,

    //
    //  main.cpp
    //  test_list_oper
    //
    //  Created by Hugo Cao  on 15/7/6.
    //  Copyright (c) 2015年 Hugo Cao . All rights reserved.
    //
    
    /*
     题目:
        输出链表中倒数第k个节点,
        输入一个链表,输出链表中倒数第K个节点,为了符合大多数人的习惯,本题从1开始计数,
     即链表的尾节点是倒数第一个是1节点,例如输入一个6个节点,
     从头节点开始,依次是1,2,3,4,5,6。倒数第三个节点是4.
     
     解题思路:
         (1) 最简单的方式,遍历一遍,然后计算倒数第k个位 n-k+1
         (2) 第二种方式,只遍历一次,用空间代替时间,设置第二个指针,让一个指针先出发,
            由于输出倒数第K个,所以,输出位置是n - k + 1.所以当前一个节点,走了K-1时,第二个出发。
     
     
     引申:这个问题,提示了一个很好的解决问题的方式,也是空间换时间很好的例证。
     (1)比如打印单链表中间的那个元素,依旧可以设置2个指针,让一个快一个慢,一个一次走1步,另一个走2步。
     (2)判断一个链表是否是循环链表,依旧可以设置一个快指针,一个慢指针,判断是否能追上另一个,如果可以追上,就是循环列表。
     */
    
    #include <stdio.h>
    #include <stdlib.h>
    #include <stack>
    #include <iostream>
    using namespace std;
    
    typedef struct ListNode
    {
        int m_nValue;
        struct ListNode *m_pNext;
    } lNode;
    
    
    //添加元素结点
    void listAddNode(lNode *head)
    {
        lNode *p = head, *p_Inter = NULL;
        
        if (!(p_Inter = ((lNode *)malloc(sizeof(lNode)))))
        {
            printf("the memery is don't create it
    ");
            return;
        }
        p_Inter->m_pNext = NULL;
        
        int data;
        printf("请输入数字:
    ");
        scanf("%d", &data);
        p_Inter->m_nValue = data;
        
        while (p->m_pNext != NULL)
        {
            p = p->m_pNext;
        }
        
        p->m_pNext = p_Inter;
        
    }
    
    
    //创建元素结点
    lNode* createList(lNode *head)
    {
        if (!(head = ((lNode *)malloc(sizeof(lNode)))))
        {
            printf("the memery is don't create it
    ");
            return NULL;
        }
        head->m_pNext = NULL;
        int data;
        printf("请输入数字:
    ");
        scanf("%d", &data);
        head->m_nValue = data;
        
        
        lNode *p = head;
        char X_cin = 'Y';
        while (true)
        {
            printf("是否继续添加:N/n 
    ");
            cin >> X_cin;
            
            if (X_cin == 'y' || X_cin == 'Y')
            {
                ;
            }
            else if (X_cin == 'N' || X_cin == 'n')
            {
                return head;
            }
            else
            {
                ;
            }
            
            listAddNode(p);
        }
        
    }
    
    
    //显示列表
    void showList(lNode *head)
    {
        if (NULL == head)
        {
            cout << "list is empty 
    " << endl;
            return;
        }
        
        lNode *p = head;
        
        while (p != NULL)
        {
            printf("%d
    ", p->m_nValue);
            p = p->m_pNext;
        }
        
    }
    
    
    //翻转链表
    void reversePut(lNode *point)
    {
        stack <int> stack_rev;
        lNode *p = point;
        
        while (p != NULL)
        {
            stack_rev.push(p->m_nValue);
            p = p->m_pNext;
        }
        
        cout << "翻转以后的输出" << endl;
        while (!stack_rev.empty())
        {
            cout << stack_rev.top() << endl;
            stack_rev.pop();
        }
    }
    
    
    //输出倒数第K个元素节点,遍历所有节点型。
    void firstPrintNode(lNode *head, int kNum)
    {
        if (head == NULL || kNum <= 0)
            return;
    
        int length = 0;
        lNode *p = head;
        
        while (p != NULL) {
            p = p->m_pNext;
            length++;
        }
        if (length < kNum)
        {
            cout << "链表长度为:" << length << ", 而遍历的节点位置是: "<< kNum << endl;
            return;
        }
        cout << "链表长度为:" << length;
        p = head;
        while (length != kNum) {
            length--;
            p =  p->m_pNext;
        }
        
        cout << "  输出倒数第K个元素节点: " << p->m_nValue << endl;
    }
    
    //输出第K个结点,第二种方式,两个指针
    void secondPrintNode(lNode *head, int kNum)
    {
        if (head == NULL || kNum <= 0)
            return;
    
        lNode *p1 = head;
        lNode *p2 = head;
        int length = kNum;
        
        while (p1 != NULL) {
            p1 = p1->m_pNext;
            length--;
            if (length < 0)
                p2 = p2->m_pNext;
        }
        
        cout << "  输出倒数第K个元素节点: " << p2->m_nValue << endl;
    }
    
    
    int main()
    {
        lNode *head = NULL;
        
        head = createList(head);
        showList(head);
        //翻转链表
        //reversePut(head);
        
        secondPrintNode(head, 3);
        
        
        return 0;
    }
  • 相关阅读:
    微软Silverlight团队关于PDC会议发表官方补充声明(风云翻译版)
    《银光志Silverlight 3.0开发详解与最佳实践》发行第三版总销量过万册
    Silverlight医学PACS诊断分析管理系统【案例分享】
    微软PDC10与最后的恐慌者
    风云的银光志Silverlight4.0教程之与学会使用Frame控件
    WPF案例之生产线控制器管理系统
    WindowsPhone7 经典3D游戏《刺客信条》评测
    Silverlight4开发的炫酷企业网站整站(运行大量特效)
    微软Windows Phone7超越Android、iOS的五大优势
    as3 滤镜学习笔记
  • 原文地址:https://www.cnblogs.com/hgonlywj/p/4842558.html
Copyright © 2011-2022 走看看