有一个长度为N的一维花园。在N长花园的每个位置,都安装了一个喷泉。给定一个数组a[] ,使得a[i]描述第i个喷泉的覆盖范围。喷泉可以覆盖从位置max(i – a[i], 1)到min(i + a[i], N) 的范围。一开始,所有的喷泉都关闭了。任务是找到需要激活的最小数量的喷泉,以便整个N 长的花园都可以被水覆盖。
例子:
Input: a[] = {1, 2, 1}
Output: 1
Explanation:
For position 1: a[1] = 1, range = 1 to 2
For position 2: a[2] = 2, range = 1 to 3
For position 3: a[3] = 1, range = 2 to 3
Therefore, the fountain at position a[2] covers the whole garden.
Therefore, the required output is 1.
Input: a[] = {2, 1, 1, 2, 1}
Output: 2
方法:该问题可以使用动态规划解决。请按照以下步骤解决问题:
- 遍历数组,对于每个数组索引,即第i个喷泉,找到当前喷泉覆盖的最左边的喷泉。
- 然后,找到上一步得到的最左边的喷泉所覆盖的最右边的喷泉,并在dp[]数组中更新。
- 初始化一个变量cntFount来存储需要激活的最小喷泉数。
- 现在,遍历dp[]数组并继续激活左侧的喷泉,覆盖当前右侧的最大喷泉,并将cntFount增加1 。最后,打印cntFount作为所需答案。
下面是上述方法的实现。
C++14
// C++ program to implement
// the above approach
#include
using namespace std;
// Function to find minimum
// number of fountains to be
// activated
int minCntFoun(int a[], int N)
{
// dp[i]: Stores the position of
// rightmost fountain that can
// be covered by water of leftmost
// fountain of the i-th fountain
int dp[N];
// initializing all dp[i] values to be -1,
// so that we don't get garbage value
for(int i=0;i
Java
// Java program to implement
// the above approach
import java.util.*;
class GFG {
// Function to find minimum
// number of fountains to be
// activated
static int minCntFoun(int a[], int N)
{
// dp[i]: Stores the position of
// rightmost fountain that can
// be covered by water of leftmost
// fountain of the i-th fountain
int[] dp = new int[N];
for(int i=0;i
Python3
# Python3 program to implement
# the above appraoch
# Function to find minimum
# number of fountains to be
# activated
def minCntFoun(a, N):
# dp[i]: Stores the position of
# rightmost fountain that can
# be covered by water of leftmost
# fountain of the i-th fountain
dp = [0] * N
for i in range(N):
dp[i] = -1
# Traverse the array
for i in range(N):
idxLeft = max(i - a[i], 0)
idxRight = min(i + (a[i] + 1), N)
dp[idxLeft] = max(dp[idxLeft],
idxRight)
# Stores count of fountains
# needed to be activated
cntfount = 1
idxRight = dp[0]
# Stores index of next fountain
# that needed to be activated
idxNext = 0
# Traverse dp[] array
for i in range(N):
idxNext = max(idxNext,
dp[i])
# If left most fountain
# cover all its range
if (i == idxRight):
cntfount += 1
idxRight = idxNext
return cntfount
# Driver code
if __name__ == '__main__':
a = [1, 2, 1]
N = len(a)
print(minCntFoun(a, N))
# This code is contributed by Shivam Singh
C#
// C# program to implement
// the above approach
using System;
class GFG {
// Function to find minimum
// number of fountains to be
// activated
static int minCntFoun(int[] a, int N)
{
// dp[i]: Stores the position of
// rightmost fountain that can
// be covered by water of leftmost
// fountain of the i-th fountain
int[] dp = new int[N];
for (int i = 0; i < N; i++)
{
dp[i] = -1;
}
// Stores index of leftmost
// fountain in the range of
// i-th fountain
int idxLeft;
// Stores index of rightmost
// fountain in the range of
// i-th fountain
int idxRight;
// Traverse the array
for (int i = 0; i < N; i++) {
idxLeft = Math.Max(i - a[i], 0);
idxRight = Math.Min(i + (a[i] + 1),
N);
dp[idxLeft] = Math.Max(dp[idxLeft],
idxRight);
}
// Stores count of fountains
// needed to be activated
int cntfount = 1;
// Stores index of next
// fountain that needed
// to be activated
int idxNext = 0;
idxRight = dp[0];
// Traverse []dp array
for (int i = 0; i < N; i++)
{
idxNext = Math.Max(idxNext, dp[i]);
// If left most fountain
// cover all its range
if (i == idxRight)
{
cntfount++;
idxRight = idxNext;
}
}
return cntfount;
}
// Driver Code
public static void Main(String[] args)
{
int[] a = { 1, 2, 1 };
int N = a.Length;
Console.Write(minCntFoun(a, N));
}
}
// This code is contributed by gauravrajput1
Javascript
输出
1
时间复杂度: O(N)
辅助空间: O(N)
如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程和学生竞争性编程现场课程。