LintCode—链表翻转(35)

本文介绍了一种链表翻转的实现方法,包括处理特殊情况如空链表、单节点链表及双节点链表的情况,并提供了详细的代码示例。

数据结构—线性结构—链表:(链表翻转)

一、题目:翻转一个链表

样例:给出一个链表1->2->3->null,这个翻转后的链表为3->2->1->null

二、分析:

        需要考虑的点:

            1、输入null;

            2、链表只有一个节点;

            3、链表有两个节点;

三、代码:

/**
 * Definition for ListNode
*/

public class ListNode {
    int val;
    ListNode next;
    ListNode(int x) {
        val = x;
        next = null;
    }
}

public class Solution {
    /**
     * @param head: n
     * @return: The new head of reversed linked list.
     */
    public ListNode reverse(ListNode head) {
            
        if(head != null && head.next != null){
            ListNode secondNode = new ListNode(0);
            ListNode thirdNode = new ListNode(0);
            secondNode = head.next;
            thirdNode = secondNode.next;
            
            head.next = null;
            while(thirdNode != null){
                secondNode.next = head;
                head = secondNode;
                secondNode = thirdNode;
                thirdNode = secondNode.next;
            }
            secondNode.next = head;
            head = secondNode;
        }
        return head;
    }
}

### LintCode 221 链表求和 II 的 C++ 实现 LintCode 221 题目描述了一个链表求和问题,其中两个链表分别表示两个正整数的位数顺序存储形式。由于题目要求处理的是正向存放数字的情况,因此需要额外考虑如何逆序操作来完成加法计算。 以下是基于此需求的一种解决方案: #### 方法概述 为了实现该功能,可以通过以下方式解决问题: 1. **反转链表**:因为输入的链表是以正向的形式存储数值,而我们需要按照反向的方式逐位相加,所以第一步是对两个链表进行反转。 2. **模拟加法过程**:通过遍历反转后的链表,逐步累加每一位上的值并记录进位情况。 3. **重新构建结果链表**:将最终的结果再次反转回来形成正确的输出格式。 --- #### 完整代码实现 ```cpp #include <iostream> using namespace std; // Definition for singly-linked list. struct ListNode { int val; ListNode *next; ListNode(int x) : val(x), next(nullptr) {} }; // Function to reverse a linked list ListNode* reverseList(ListNode* head) { ListNode* prev = nullptr; ListNode* curr = head; while (curr != nullptr) { ListNode* tempNext = curr->next; // Store the next node temporarily curr->next = prev; // Reverse pointer direction prev = curr; // Move forward in original list curr = tempNext; // Proceed to next node } return prev; // New head is 'prev' } // Function to add two numbers represented by reversed linked lists ListNode* addTwoNumbersReversed(ListNode* l1, ListNode* l2) { ListNode dummy(0); ListNode* tail = &dummy; int carry = 0; while (l1 || l2 || carry) { int sum = (l1 ? l1->val : 0) + (l2 ? l2->val : 0) + carry; carry = sum / 10; tail->next = new ListNode(sum % 10); // Create new node with current digit tail = tail->next; if (l1) l1 = l1->next; if (l2) l2 = l2->next; } return dummy.next; } // Main function to solve problem as per description ListNode* addListsII(ListNode* l1, ListNode* l2) { // Step 1: Reverse both input lists l1 = reverseList(l1)[^1]; l2 = reverseList(l2); // Step 2: Add them together using helper method on reversed versions ListNode* resultRev = addTwoNumbersReversed(l1, l2); // Step 3: Reverse final answer back into correct order and return it return reverseList(resultRev); } ``` --- #### 关键点解析 1. **链表反转逻辑** - 使用迭代方法实现了 `reverseList` 函数,时间复杂度为 \(O(n)\),空间复杂度为 \(O(1)\)。 2. **加法规则** - 对于每一个节点位置,都需要考虑到可能存在的进位情况,并将其传递到下一位运算中[^2]。 3. **结果重建** - 计算完成后得到的新链表仍然是反向排列的状态,最后一步再调用一次 `reverseList` 将其恢复成正常次序返回给用户[^3]。 --- #### 时间与空间复杂度分析 - **时间复杂度**: 整体流程涉及三次完整的链表扫描(两次用于翻转以及一次执行实际加总),故总体时间为线性的,即 \(O(m+n)\),这里 m 和 n 分别代表两条初始链表长度。 - **空间复杂度**: 主要是用来创建新的节点构成答案部分所消耗的空间资源,同样也是 \(O(\max(m,n))\) 级别大小。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值