(java)leetcode-25

Reverse Nodes in k-Group

Given a linked list, reverse the nodes of a linked list k at a time and return its modified list.

k is a positive integer and is less than or equal to the length of the linked list. If the number of nodes is not a multiple of k then left-out nodes in the end should remain as it is.

You may not alter the values in the nodes, only nodes itself may be changed.

Only constant memory is allowed.

For example,
Given this linked list: 1->2->3->4->5

For k = 2, you should return: 2->1->4->3->5

For k = 3, you should return: 3->2->1->4->5


解题思路:

这道题跟24题是有些相似的,在这里我也大概借鉴了24的题方法。不过在这里利用了递归来进行求解。

(1)首先先定义一个first,让first.next = head,然后让p = first,a = 0。不断地令p = p.next,a++,当遇到p.next == null时证明遍历到最后,返回null,如果当a == k-1时,证明下一个节点就是我们要开始进行反转的节点,在例子k = 3中就是当p时节点2,p.next为节点3的时候。

(2)此时要开始反转了,反转的过程跟24题一样。q = p.next,p.next = q.next,q.next = p,这个时候节点3.next = 节点2,节点2.next = 4。返回节点3,因为最后还要更新first.next = 节点3。
(3)当3的反转结束之后就要退回去进行节点1跟节点2的反转,道理同上,反转之后节点2.next = 节点1,节点1.next = 节点4。继续返回节点3,不断递归回去就能得到一次反转。

(4)首先获取原来的first.next,即节点1,因为下一次反转的时候就是要从节点1.next = 节点4开始遍历。再更新first.next = 节点3,此时就完成了前k个node的反转。
(5)下一次的递归就从节点1的next进行查找,不断递归直到节点.next == null结束。

感觉我这个讲起来比较繁琐,但是还是比较好理解的吧。


/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
public class Solution {
    public ListNode reverseKGroup(ListNode head, int k) 
	{
		ListNode first = new ListNode(0);
		first.next = head;
		int a = 0;
		if(k == 1)
			return first.next;
		change(first,a,k);
		return first.next;
    }
	public ListNode change(ListNode p,int a,int k)
	{
	    //下一个节点为null,证明查找结束
		if(p.next == null)
			return null;
		ListNode result = null;
		if(a < k-1)
		{
		    //递归下一节点
			result = change(p.next,a+1,k);
			//证明查找结束
			if(result == null)
				return result;
			//a = 0证明这是起始节点,进行更新
			if(a == 0)
			{
				ListNode r = p.next;
				p.next = result;
				return change(r,a,k);
			}
		}
		//进行节点反转
		ListNode q = p.next;
		p.next = q.next;
		q.next = p;
		//返回节点作为第一次的first.next更新,以及之后的节点更新(例如在k = 3,1->2->3->4->5->6中,第二次反转即4->5->6的反转中,返回6作为1.next)
		if(a == k-1)
			result = q;
		return result;
	}
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Java中使用LeetCode是一种常见的方式来练习和提高算法和数据结构的能力。LeetCode提供了大量的算法题目,每个题目都有一个特定的要求和限制条件。在解题过程中,我们需要按照题目要求设计和实现解决方案。 对于JavaLeetCode编程,一般我们会按照以下步骤进行: 1. 阅读题目:仔细阅读题目的要求和限制条件,理解题目的意思。 2. 分析问题:根据题目的要求和限制条件,考虑可用的算法和数据结构来解决问题。可以使用图、树、链表、数组、哈希表等数据结构,以及常见的算法如深度优先搜索、广度优先搜索、动态规划、回溯等。 3. 实现算法:使用Java编写算法的解决方案。根据题目的要求,我们可以使用类、方法等来组织和实现代码。 4. 编写测试用例:为了验证解决方案的正确性,编写测试用例是必不可少的。测试用例应该包括各种情况,包括边界情况和一般情况。 5. 运行和测试:运行编写的代码,并使用编写的测试用例进行测试。通过测试用例的执行结果,我们可以判断代码的正确性和性能。 在编写测试用例时,我们应该考虑尽可能多的情况,以确保代码的正确性。测试用例应该包括输入数据和预期输出结果。可以使用JUnit等测试框架来组织和运行测试用例。 总结来说,JavaLeetCode编程需要认真阅读题目,分析问题,设计具体的解决方案,并使用合适的数据结构和算法进行实现。编写测试用例是验证解决方案正确性的重要步骤,可以使用JUnit等测试框架来辅助进行测试。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值