英文:
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 < 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 {
//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 < arr.length - k + 1; j++) {
boolean found = false;
for (int x = j; x < j + k; x++) {
if (arr[x] < 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 >= 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]);
}
}
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 < arr.length - k + 1; i++) {
if(index < i) {
// Find the index of the next negative number
do {
index++;
} while (index < arr.length && arr[index] >= 0);
}
// If the next negative number is within the window print it,
// otherwise print "0"
System.out.println(index < 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<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;
}
答案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<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){
// queue.add(A[j]);
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;
}
// queue.add((long)0);
}
if(endWindow>=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 < $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, ", ");
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论