Open In App

Minimum candies to distribute among children based on given conditions

Last Updated : 28 Mar, 2025
Comments
Improve
Suggest changes
Like Article
Like
Report

Given an array arr[] consisting of n positive integers representing the ratings of n children, the task is to find the minimum number of candies required for distributing to n children such that every child gets at least one candy and the children with the higher rating get more candies than its neighbors.

Examples:

Input: arr[] = [15, 40, 32, 12, 17, 23]
Output: 12
Explanation: Children at index 0 and 3 will get 1 candies each as their rating is higher than index 1 and 5 will get 3 candy and index 2 and 4 will get two candy . Thus total candies = 1 +2 + 3 + 1 + 2 +3 = 12

Input: arr[] = [1, 2, 2]
Output: 4
Explanation: You can allocate to the first, second and third child with 1, 2, 1 candies respectively.
The third child gets 1 candy because it satisfies the above two conditions.

[Naive Approach] Two pass Greedy Approach - O(n) Time and O(n) Space

The approach used in this code ensures that students with higher scores get more candies than their adjacent peers by utilizing two passes over the array. First, an initial left-to-right pass assigns each student at least one candy and increases the count when a student's score is higher than the previous one. Next, a right-to-left pass ensures that if a student's score is higher than the next student’s, they receive more candies than them. Finally, the result is computed by summing the maximum candy count from both passes for each student, ensuring fairness while maintaining minimal distribution.


C++
#include <bits/stdc++.h>
using namespace std;

int minCandy(vector<int> &arr)
{
    int n = arr.size();
    if (n == 0)
        return 0; // Edge case

    vector<int> leftcandy(n, 1);
    vector<int> rightcandy(n, 1);

    // Left pass
    for (int i = 1; i < n; i++)
    {
        if (arr[i] > arr[i - 1])
            leftcandy[i] = leftcandy[i - 1] + 1;
    }

    // Right pass
    for (int i = n - 2; i >= 0; i--)
    {
        if (arr[i] > arr[i + 1])
            rightcandy[i] = rightcandy[i + 1] + 1;
    }

    // Calculate final answer
    int ans = 0;
    for (int i = 0; i < n; i++)
    {
        ans += max(leftcandy[i], rightcandy[i]); // Take max at each position
    }

    return ans;
}

int main()
{
    vector<int> arr = {15, 40, 32, 12, 17, 23};

    cout << minCandy(arr);
}
Java
import java.util.*;

public class Main {
    public static int minCandy(int[] arr)
    {
        int n = arr.length;
        if (n == 0)
            return 0; // Edge case

        int[] leftCandy = new int[n];
        int[] rightCandy = new int[n];
        Arrays.fill(leftCandy, 1);
        Arrays.fill(rightCandy, 1);

        // Left pass
        for (int i = 1; i < n; i++) {
            if (arr[i] > arr[i - 1])
                leftCandy[i] = leftCandy[i - 1] + 1;
        }

        // Right pass
        for (int i = n - 2; i >= 0; i--) {
            if (arr[i] > arr[i + 1])
                rightCandy[i] = rightCandy[i + 1] + 1;
        }

        // Calculate final answer
        int ans = 0;
        for (int i = 0; i < n; i++) {
            ans += Math.max(
                leftCandy[i],
                rightCandy[i]); // Take max at each position
        }

        return ans;
    }

    public static void main(String[] args)
    {
        int[] arr = { 15, 40, 32, 12, 17, 23 };

        System.out.println(minCandy(arr));
    }
}
Python
import array


def minCandy(arr):
    n = len(arr)
    if n == 0:
        return 0  # Edge case

    leftcandy = array.array('i', [1] * n)
    rightcandy = array.array('i', [1] * n)

    # Left pass
    for i in range(1, n):
        if arr[i] > arr[i - 1]:
            leftcandy[i] = leftcandy[i - 1] + 1

    # Right pass
    for i in range(n - 2, -1, -1):
        if arr[i] > arr[i + 1]:
            rightcandy[i] = rightcandy[i + 1] + 1

    # Calculate final answer
    return sum(max(leftcandy[i], rightcandy[i]) for i in range(n))


# Driver code
arr = array.array('i', [15, 40, 32, 12, 17, 23])
print(minCandy(arr))
C#
using System;

class Program {
    static int minCandy(int[] arr)
    {
        int n = arr.Length;
        if (n == 0)
            return 0; // Edge case

        int[] leftCandy = new int[n];
        int[] rightCandy = new int[n];

        Array.Fill(leftCandy, 1);
        Array.Fill(rightCandy, 1);

        // Left pass
        for (int i = 1; i < n; i++) {
            if (arr[i] > arr[i - 1])
                leftCandy[i] = leftCandy[i - 1] + 1;
        }

        // Right pass
        for (int i = n - 2; i >= 0; i--) {
            if (arr[i] > arr[i + 1])
                rightCandy[i] = rightCandy[i + 1] + 1;
        }

        // Calculate final answer
        int ans = 0;
        for (int i = 0; i < n; i++) {
            ans += Math.Max(leftCandy[i], rightCandy[i]);
        }

        return ans;
    }

    static void Main()
    {
        int[] arr = { 15, 40, 32, 12, 17, 23 };
        Console.WriteLine(minCandy(arr));
    }
}
JavaScript
function minCandy(arr)
{
    let n = arr.length;
    if (n === 0)
        return 0; // Edge case

    let leftCandy = new Array(n).fill(1);
    let rightCandy = new Array(n).fill(1);

    // Left pass
    for (let i = 1; i < n; i++) {
        if (arr[i] > arr[i - 1]) {
            leftCandy[i] = leftCandy[i - 1] + 1;
        }
    }

    // Right pass
    for (let i = n - 2; i >= 0; i--) {
        if (arr[i] > arr[i + 1]) {
            rightCandy[i] = rightCandy[i + 1] + 1;
        }
    }

    // Calculate final answer
    let ans = 0;
    for (let i = 0; i < n; i++) {
        ans += Math.max(leftCandy[i], rightCandy[i]);
    }

    return ans;
}

// Driver code
let arr = [ 15, 40, 32, 12, 17, 23 ];
console.log(minCandy(arr));

Output
12

[Expected Approach] Peak-Valley Greedy Approach - O(n) Time and O(1) Space

The idea is to find the local peak and local valley for each continuous increasing or decreasing subsequence and add then to total value. To do so, start the the 0th index, and check if current rating arr[i] > arr[i-1], if so increment the local peak and add the value in ans. Similarly, generate local valley and add the result in final answer. At last remove the min(peak, valley) from ans, as it get added twice.


C++
// C++ program to find number of
// candies to distribute
#include <bits/stdc++.h>
using namespace std;

// Function to find minimum candy
// required to distribute
int minCandy(vector<int> &arr)
{
    int n = arr.size();

    // create variable to store count
    // of candies, initlize it with n
    int total = n;
    int i = 1;

    // Traverse from left to right
    while (i < n)
    {

        // if rating of ith children is
        // equal to the previous children
        if (arr[i] == arr[i - 1])
        {
            i++;
            continue;
        }

        // to find the increasing sequence
        int peak = 0;
        while (i < n && arr[i] > arr[i - 1])
        {
            peak++;
            total += peak;
            i++;
        }

        if (i == n)
        {
            return total;
        }

        // to find the decreasing sequence
        int valley = 0;
        while (i < n && arr[i] < arr[i - 1])
        {
            valley++;
            total += valley;
            i++;
        }

        // remove the extra candy added twice
        total -= min(peak, valley);
    }

    return total;
}

int main()
{
    vector<int> arr = {15, 40, 32, 12, 17, 23};
    cout << minCandy(arr);
    return 0;
}
Java
// Java program to find number of
// candies to distribute
class GfG {

    // Function to find minimum candy
    // required to distribute
    static int minCandy(int[] arr)
    {
        int n = arr.length;

        // create variable to store count
        // of candies, initialize it with n
        int total = n;
        int i = 1;

        // Traverse from left to right
        while (i < n) {

            // if rating of ith children is
            // equal to the previous children
            if (arr[i] == arr[i - 1]) {
                i++;
                continue;
            }

            // to find the increasing sequence
            int peak = 0;
            while (i < n && arr[i] > arr[i - 1]) {
                peak++;
                total += peak;
                i++;
            }

            if (i == n) {
                return total;
            }

            // to find the decreasing sequence
            int valley = 0;
            while (i < n && arr[i] < arr[i - 1]) {
                valley++;
                total += valley;
                i++;
            }

            // remove the extra candy added twice
            total -= Math.min(peak, valley);
        }

        return total;
    }

    public static void main(String[] args)
    {
        int[] arr = { 15, 40, 32, 12, 17, 23 };
        System.out.println(minCandy(arr));
    }
}
Python
# Python program to find number of
# candies to distribute

# Function to find minimum candy
# required to distribute
def minCandy(arr):
    n = len(arr)

    # create variable to store count
    # of candies, initialize it with n
    total = n
    i = 1

    # Traverse from left to right
    while i < n:

        # if rating of ith children is
        # equal to the previous children
        if arr[i] == arr[i - 1]:
            i += 1
            continue

        # to find the increasing sequence
        peak = 0
        while i < n and arr[i] > arr[i - 1]:
            peak += 1
            total += peak
            i += 1

        if i == n:
            return total

        # to find the decreasing sequence
        valley = 0
        while i < n and arr[i] < arr[i - 1]:
            valley += 1
            total += valley
            i += 1

        # remove the extra candy added twice
        total -= min(peak, valley)

    return total


if __name__ == "__main__":
    arr = [15, 40, 32, 12, 17, 23]
    print(minCandy(arr))
C#
// C# program to find number of
// candies to distribute
using System;

class GfG {

    // Function to find minimum candy
    // required to distribute
    static int minCandy(int[] arr)
    {
        int n = arr.Length;

        // create variable to store count
        // of candies, initialize it with n
        int total = n;
        int i = 1;

        // Traverse from left to right
        while (i < n) {

            // if rating of ith children is
            // equal to the previous children
            if (arr[i] == arr[i - 1]) {
                i++;
                continue;
            }

            // to find the increasing sequence
            int peak = 0;
            while (i < n && arr[i] > arr[i - 1]) {
                peak++;
                total += peak;
                i++;
            }

            if (i == n) {
                return total;
            }

            // to find the decreasing sequence
            int valley = 0;
            while (i < n && arr[i] < arr[i - 1]) {
                valley++;
                total += valley;
                i++;
            }

            // remove the extra candy added twice
            total -= Math.Min(peak, valley);
        }

        return total;
    }

    public static void Main()
    {
        int[] arr = { 15, 40, 32, 12, 17, 23 };
        Console.WriteLine(minCandy(arr));
    }
}
JavaScript
// JavaScript program to find number of
// candies to distribute

// Function to find minimum candy
// required to distribute
function minCandy(arr)
{
    const n = arr.length;

    // create variable to store count
    // of candies, initialize it with n
    let total = n;
    let i = 1;

    // Traverse from left to right
    while (i < n) {

        // if rating of ith children is
        // equal to the previous children
        if (arr[i] === arr[i - 1]) {
            i++;
            continue;
        }

        // to find the increasing sequence
        let peak = 0;
        while (i < n && arr[i] > arr[i - 1]) {
            peak++;
            total += peak;
            i++;
        }

        if (i === n) {
            return total;
        }

        // to find the decreasing sequence
        let valley = 0;
        while (i < n && arr[i] < arr[i - 1]) {
            valley++;
            total += valley;
            i++;
        }

        // remove the extra candy added twice
        total -= Math.min(peak, valley);
    }

    return total;
}

const arr = [ 15, 40, 32, 12, 17, 23 ];
console.log(minCandy(arr));

Output
12



Minimum Candies Required for Distribution | DSA Problem
Article Tags :

Similar Reads