• Leetcode: Circular Array Loop


    You are given an array of positive and negative integers. If a number n at an index is positive, then move forward n steps. Conversely, if it's negative (-n), move backward n steps. Assume the first element of the array is forward next to the last element, and the last element is backward next to the first element. Determine if there is a loop in this array. A loop starts and ends at a particular index with more than 1 element along the loop. The loop must be "forward" or "backward'.
    
    Example 1: Given the array [2, -1, 1, 2, 2], there is a loop, from index 0 -> 2 -> 3 -> 0.
    
    Example 2: Given the array [-1, 2], there is no loop.
    
    Note: The given array is guaranteed to contain no element "0".
    
    Can you do it in O(n) time complexity and O(1) space complexity?

    注意The loop must be "forward" or "backward'. 所以这就是为什么[-2, 1, -1, -2, -2]是false的原因

    Just think it as finding a loop in Linkedlist, except that loops with only 1 element do not count. Use a slow and fast pointer, slow pointer moves 1 step a time while fast pointer moves 2 steps a time. If there is a loop (fast == slow), we return true, just except there's only 1 element in the loop. else if we meet element with different directions, then the search fail, we set all elements along the way to 0. Because 0 is fail for sure so when later search meet 0 we know the search will fail.

     1 public class Solution {
     2     int[] arr;
     3     public boolean circularArrayLoop(int[] nums) {
     4         arr = nums;
     5         for (int i=0; i<nums.length; i++) {
     6             if (nums[i] == 0) continue;
     7             //two pointers
     8             int j=i, k=shift(i);
     9             while (nums[i]*nums[k]>0 && nums[i]*nums[shift(k)]>0) {
    10                 if (j == k) {
    11                     // check for loop with only one element
    12                     if (j == shift(j)) break;
    13                     return true;
    14                 }
    15                 j = shift(j);
    16                 k = shift(shift(k));
    17             }
    18             // loop not found, set all element along the way to 0
    19             j = i;
    20             int val = nums[i];
    21             while (nums[j]*val > 0) {
    22                 int next = shift(j);
    23                 nums[j] = 0;
    24                 j = next;
    25             }
    26         }
    27         return false;
    28     }
    29     
    30     public int shift(int pos) {
    31         return (pos+arr[pos]+arr.length) % arr.length;
    32     }
    33 }

     Solution 2: 更清晰,没有找到Loop就set为0不是必需的

     1 public class Solution {
     2     int[] arr;
     3     public boolean circularArrayLoop(int[] nums) {
     4         arr = nums;
     5         for (int i=0; i<nums.length; i++) {
     6             if (nums[i] == 0) continue;
     7             //two pointers
     8             int j=i, k=i;
     9             while (nums[i]*nums[shift(k)]>0 && nums[i]*nums[shift(shift(k))]>0) {
    10                 j = shift(j);
    11                 k = shift(shift(k));
    12                 if (j == k) {
    13                     // check for loop with only one element
    14                     if (j == shift(j)) break;
    15                     return true;
    16                 }
    17             }
    18             // loop not found, set all element along the way to 0, not necessary
    19 
    20         }
    21         return false;
    22     }
    23     
    24     public int shift(int pos) {
    25         return (pos+arr[pos]+arr.length) % arr.length;
    26     }
    27 }
  • 相关阅读:
    生成器笔记
    迭代器笔记
    hashilib_module
    Ubuntu操作及各种命令笔记
    python正则表达式2
    python正则表达式1
    python文件操作(with关键字)
    python文件操作
    python包
    python模块
  • 原文地址:https://www.cnblogs.com/EdwardLiu/p/6202015.html
Copyright © 2020-2023  润新知