首个大小为 k 的窗口中负整数,辅助空间复杂度为 O(1),时间复杂度为 O(n)。

huangapple go评论92阅读模式
英文:

First negative integer in every window of size k with auxiliary space O(1) and O(n) time complexity

问题

给定一个数组和一个正整数 k找到每个大小为 k 的窗口连续子数组中第一个负整数如果窗口不包含负整数则对应窗口打印 0

package com.slidingwindow;

public class demo2 {

    public static void maximum(int arr[], int k) {
        int index = -1;
        boolean flag = false;

        int i = 0, j = 0, sum = 0;

        while (j < arr.length) {

            if (arr[j] < 0 && !flag) {
                index = j;
                flag = true;
                System.out.println(arr[index]);
            }

            if (j - i + 1 < k) {
                j++;

            } else if (j - i + 1 == k) {

                if (!flag) {
                    System.out.println("0");
                    i++;
                    j++;
                } else {
                    // 滑动窗口,通过增加 i 和 j
                    i++;
                    j++;
                    flag = false;
                }

            }
        }
    }

    public static void main(String[] args) {
        int arr[] = { -2, 5, 1, 8, -2, 9, -1 };
        int k = 2;
        maximum(arr, k);
    }
}

预期输出

-2

0

0

-2

-2

-1

实际输出

-2

0

0

-2

0

-1

英文:

Given an array and a positive integer k, find the first negative integer for each window(contiguous subarray) of size k. If a window does not contain a negative integer, then print 0 for that window.

package com.slidingwindow;
public class demo2 {
public static void  maximum(int arr[], int k) {
int index = -1;
boolean flag = false;
int i = 0, j = 0, sum = 0;
while (j &lt; arr.length) {
if(arr[j]&lt;0 &amp;&amp; !flag) {
index =j;
flag = true;
System.out.println(arr[index]);
}
if (j - i + 1 &lt; k) {
j++;
} else if (j - i + 1 == k) {
if(!flag) {
System.out.println(&quot;0&quot;);
i++;
j++;
}else {
//slide window by incrementing i and j
i++;
j++;
flag = false;a
}
}
}
}
public static void main(String[] args) {
int arr[] = { -2, 5, 1, 8, -2, 9, -1 };
int k = 2;
maximum(arr, k);
}
}

Expected output

-2

0

0

-2

-2

-1

Actual

-2

0

0

-2

0

-1

答案1

得分: 2

我试图理解您的逻辑但我不能完全理解以下是我从头开始创建的内容

class demo2:

    def maximum(arr, k):
        for j in range(len(arr) - k + 1):
            found = False
            for x in range(j, j + k):
                if arr[x] < 0:
                    print(arr[x])
                    found = True
                    break
            if not found:
                print(0)

    arr = [-2, 5, 1, 8, -2, 9, -1]
    k = 2
    maximum(arr, k)

结果:

-2
0
0
-2
-2
-1

我认识到在数组长度和窗口大小都显著大的情况下,可能有更有效的方法来做到这一点。但是您的问题并没有说明是这种情况。这是一个您需要确保自己是否想花时间在简单明了的解决方案之外进行优化的地方。

英文:

I tried to understand your logic, but I couldn't quite get it. Here's what I came up with, starting pretty much from scratch:

class demo2 {
public static void maximum (int arr[], int k){
for (int j = 0; j &lt; arr.length - k + 1; j++) {
boolean found = false;
for (int x = j; x &lt; j + k; x++) {
if (arr[x] &lt; 0) {
System.out.println(arr[x]);
found = true;
break;
}
}
if (!found)
System.out.println(0);
}
}
public static void main(String[] args) {
int arr[] = { -2, 5, 1, 8, -2, 9, -1 };
int k = 2;
maximum(arr, k);
}
}

Result:

-2
0
0
-2
-2
-1

I recognize that there might be a more efficient way of doing this to the point that it would matter, if both the array length and the window size were significantly large. But your question doesn't state that this is the case. This is a place where you need to be sure you want to spend the time to optimize beyond the simple and obvious solution.

答案2

得分: 0

可以使用真实的线性复杂度 O(n) 来实现它(与朴素实现的多项式复杂度 O(n*k) 相反):

public static void maximum (int arr[], int k) {
    int index = -1;
    for (int i = arr.length - 1; i >= 0; i--) {
        if (index >= i + k) {
            index = -1;
        }
        if (arr[i] < 0) {
            index = i;
        }
        arr[i] = index >= 0 ? arr[index] : 0;
    }
    for(int i = 0; i <= arr.length - k; i++) {
        System.out.println(arr[i]);
    }
}

更新: 或者甚至更好,不对 arr 数组进行写入操作:

public static void maximum (int arr[], int k) {
    int index = -1;
    for (int i = 0; i < arr.length - k + 1; i++) {
        if(index < i) {
            // 找到下一个负数的索引
            do {
                index++;
            } while (index < arr.length && arr[index] >= 0);
        }
        // 如果下一个负数在窗口内则打印它,否则打印 "0"
        System.out.println(index < i + k ? arr[index] : 0);
    }
}

关于内部循环(最坏情况下,即表中没有负数)的迭代次数方面,与朴素算法 O(n*k) 进行比较:

            | 朴素        | 动态    |
| O((n-m+1)*m) | O(n)    |
--------------------------------------
n=7,  m=2 |           12 |       7 |
n=10,  m=2 |           18 |      10 |
n=100, m=10 |          910 |     100 |
n=100, m=50 |         2550 |     100 |     
英文:

It can be implemented with real linear complexity O(n) (as opposite to the naive implementation with <s>polynomial</s> complexity O(n*k)):

public static void maximum (int arr[], int k) {
    int index = -1;
    for (int i = arr.length - 1; i &gt;= 0; i--) {
        if (index &gt;= i + k) {
            index = -1;
        }
        if (arr[i] &lt; 0) {
            index = i;
        }
        arr[i] = index &gt;= 0 ? arr[index] : 0;
    }
    for(int i = 0; i &lt;= arr.length - k; i++) {
        System.out.println(arr[i]);
    }
}

UPDATE: or even better, without writing to the arr array:

public static void maximum (int arr[], int k) {
    int index = -1;
    for (int i = 0; i &lt; arr.length - k + 1; i++) {
        if(index &lt; i) {
            // Find the index of the next negative number
            do {
                index++;
            } while (index &lt; arr.length &amp;&amp; arr[index] &gt;= 0);
        }
        // If the next negative number is within the window print it,
        // otherwise print &quot;0&quot;
        System.out.println(index &lt; i + k ? arr[index] : 0);
    }
}

Comparison with the naive algorithm O(n*k) in terms of the number of iterations of the (internal) loop (worst case scenario, i.e. when there are no negative numbers in the table at all):

            | naive        | dynamic |
| O((n-m+1)*m) | O(n)    |
--------------------------------------
n=7,  m=2 |           12 |       7 |
n=10,  m=2 |           18 |      10 |
n=100, m=10 |          910 |     100 |
n=100, m=50 |         2550 |     100 |     

答案3

得分: 0

vector<int> firstNegative(vector<int> arr, int lenn, int k)
{
  vector<int> ans;
  int start = 0, end = 0;
  queue<int> index;
  while(start <= lenn-k)
  {
    if(arr[end] < 0)
      index.push(end);

      
    if(k == (end-start+1))
    {
      if(index.empty())
        ans.push_back(0);
      else
      {
        if(index.front()>=start && index.front()<=end)
          ans.push_back(arr[index.front()]);
        else
        {
          index.pop();
          continue;
        }
      }
      start++;
    }
    end++;
  }
  return ans;
}
英文:

I have a c++ solution, also i have submitted this code on gfgs practice problem and it got accepted. Time complexity is O(n) and auxiliary space complexity is O(K)

vector&lt;int&gt; firstNegative(vector&lt;int&gt; arr, int lenn, int k)
{
vector &lt;int&gt; ans;
int start = 0, end = 0;
queue &lt;int&gt; index;
while(start &lt;= lenn-k)
{
if(arr[end] &lt; 0)
index.push(end);
if(k == (end-start+1))
{
if(index.empty())
ans.push_back(0);
else
{
if(index.front()&gt;=start &amp;&amp; index.front()&lt;=end)
ans.push_back(arr[index.front()]);
else
{
index.pop();
continue;
}
}
start++;
}
end++;
}
return ans;
}

答案4

得分: 0

Deque<Long> queue = new LinkedList<>();
int C = N - K + 1;
long[] output = new long[C];
int c = -1;
int startWindow = 0;
int endWindow = K;
boolean firstFlag = true;
while (true) {
    for (int j = startWindow; j < endWindow; j++) {
        if (A[j] < 0 && firstFlag) {
            if (c < C - 1) {
                output[++c] = A[j];
            }
            firstFlag = false;
            break;
        }
        if (j >= N - 1) {
            break;
        }
    }
    if (firstFlag) {
        if (c < C - 1) {
            output[++c] = 0;
        }
    }
    if (endWindow >= N) {
        break;
    }
    firstFlag = true;
    startWindow = startWindow + K - 1;
    endWindow = startWindow + K;
}
return output;
英文:
     Deque&lt;Long&gt; queue = new LinkedList&lt;&gt;();
int C=N-K+1;
long[] output = new long[C];
int c = -1;
int startWindow = 0;
int endWindow =K;
boolean firstFlag=true;
while (true) {
for(int j=startWindow;j&lt;endWindow;j++){
if(A[j] &lt; 0 &amp;&amp; firstFlag){
//  queue.add(A[j]);
if(c&lt;C-1){
output[++c]=A[j];
}
firstFlag=false;
break;
}
if(j&gt;=N-1) {
break;
}
}
if(firstFlag){
if(c&lt;C-1){
output[++c]=0;
}
//  queue.add((long)0);
}
if(endWindow&gt;=N){
break;
}
firstFlag=true;
startWindow=startWindow+K-1;
endWindow=startWindow+K;
}
// 		while(!queue.isEmpty())
// 		      output[++c] = queue.remove();
return output;

答案5

得分: 0

function one_loop() {

    $arr = [-12, -1, 7, -8, 15, 30, -16, -30, 40, 3];
    $arr_len = count($arr); // 10
    $result = [];
    $k = 2;
    $i = 0;
    $j = 0;

    while ($j < $arr_len && $i < $arr_len-$k+1) {
        $flag = false;
        $window_size = $j-$i+1;
        if($arr[$j] < 0) {
            array_push($result, $arr[$j]);
            $flag = true;
        }
        if($window_size == $k && $flag == false){
            array_push($result, 0);
            $i++;
            $j = $i;
        } elseif ($flag == true) {
            $i++;
            $j = $i;
        } elseif ($flag == false && $window_size != $k) {
            $j++;
        }
    }
    echo implode($result, ", ");
}
英文:
function one_loop() {
$arr = [-12, -1, 7, -8, 15, 30, -16, -30, 40, 3];
$arr_len = count($arr); // 7
$result = [];
$k = 2;
$i = 0;
$j = 0;
while ($j &lt; $arr_len &amp;&amp; $i &lt; $arr_len-$k+1) {       
$flag = false;
$window_size = $j-$i+1;
if($arr[$j] &lt; 0) {
array_push($result, $arr[$j]);
$flag = true;
}
if($window_size == $k &amp;&amp; $flag == false){
array_push($result, 0);
$i++;
$j = $i;
} elseif ($flag == true) {
$i++;
$j = $i;
} elseif ($flag == false &amp;&amp; $window_size != $k) {
$j++;
}
}
echo implode($result, &quot;, &quot;);
}

huangapple
  • 本文由 发表于 2020年10月18日 02:36:16
  • 转载请务必保留本文链接:https://go.coder-hub.com/64406006.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定