Gym Energy Problem
Today you decided to go to the gym. You currently have E energy. There are N exercises in the gym. Each of these exercises drains A[i] amount of energy from your body.
 |
Infosys HackWithInfy 2025 |
You feel tired if your energy reaches 0 or below. Calculate the minimum number of exercises you have to perform such that you become tired. Every unique exercise can only be performed at most 2 times as others also have to use the machines.
If performing all the exercises does not make you feel tired, return -1.
Parameters:
- E :: INTEGER The first line contains an integer, E, denoting the Energy. E :: 1 -> 10^5
- N :: INTEGER The next line contains an integer, N, denoting the number of exercises. N :: 1 -> 10^5
- A :: INTEGER ARRAY Each line i of the N subsequent lines (where 0 ≤ i < N) contains an integer describing the amount of energy drained by ith exercise.
A[i] :: 1 -> 10^5
Examples:
Case# 1
Input:
6
2
1
2
Output:
4
E = 6
Do 1st exercise 2 times,
Do 2nd exercise 2 times.
Hence, total exercises done = 4.
Case# 2
Input:
10
2
1
2
Output:
-1
E = 10
By doing both the exercises 2 times,
you won’t feel tired.
Case# 3
Input:
2
3
1
5
2
Output:
1
E = 2
Use 3rd exercise 1 time.
Hence, total exercises done = 1.
 |
Infosys HackWithInfy 2025 |
Python Code: Minimum Exercises to Become Tired
def min_exercises_to_tired(E, N, A):
"""
Calculate minimum number of exercises needed to become tired.
Args:
E (int): Initial energy
N (int): Number of exercises
A (list): List of energy drain values for each exercise
Returns:
int: Minimum number of exercises needed, or -1 if impossible
"""
exercises = [(drain, i) for i, drain in enumerate(A)]
exercises.sort(reverse=True)
total_energy_possible = 0
count_exercises = 0
for drain, _ in exercises:
for _ in range(2):
if total_energy_possible < E:
total_energy_possible += drain
count_exercises += 1
if total_energy_possible >= E:
return count_exercises
return -1
# Test cases
def run_test_cases():
print("Test Case 1:")
E1, N1 = 6, 2
A1 = [1, 2]
result1 = min_exercises_to_tired(E1, N1, A1)
print(f"Expected: 4, Got: {result1}")
print("\nTest Case 2:")
E2, N2 = 10, 2
A2 = [1, 2]
result2 = min_exercises_to_tired(E2, N2, A2)
print(f"Expected: -1, Got: {result2}")
print("\nTest Case 3:")
E3, N3 = 2, 3
A3 = [1, 5, 2]
result3 = min_exercises_to_tired(E3, N3, A3)
print(f"Expected: 1, Got: {result3}")
if __name__ == "__main__":
run_test_cases()
Explanation of min_exercises_to_tired
Function
Function Parameters:
- E: Initial energy level
- N: Number of exercises
- A: List of energy drain values for each exercise
Algorithm:
- Sorts exercises by energy drain in descending order to optimize for the minimum number of exercises.
- Tries each exercise up to 2 times (as per the constraint).
- Keeps track of total energy drained and the number of exercises performed.
- Returns as soon as the energy threshold is reached.
- Returns
-1
if it's impossible to reach the tired state.
Test Case Analysis:
- Case 1: Returns
4
(using exercise 1 twice and exercise 2 twice).
- Case 2: Returns
-1
(can't reach tired state).
- Case 3: Returns
1
(using the 5-energy exercise once).
Java Code: Minimum Exercises to Become Tired
public class ExerciseCalculator {
public static int minExercisesToTired(int E, int N, int[] A) {
// Create array of Exercise objects to store energy drain and original index
Exercise[] exercises = new Exercise[N];
for (int i = 0; i < N; i++) {
exercises[i] = new Exercise(A[i], i);
}
// Sort exercises by energy drain in descending order
java.util.Arrays.sort(exercises, (a, b) -> b.drain - a.drain);
int totalEnergyPossible = 0;
int countExercises = 0;
// Try each exercise up to 2 times
for (Exercise exercise : exercises) {
// Can use each exercise up to 2 times
for (int i = 0; i < 2; i++) {
if (totalEnergyPossible < E) {
totalEnergyPossible += exercise.drain;
countExercises++;
// If we've reached or exceeded the energy threshold
if (totalEnergyPossible >= E) {
return countExercises;
}
}
}
}
// If we can't drain enough energy even using all exercises twice
return -1;
}
// Helper class to store exercise information
static class Exercise {
int drain;
int index;
Exercise(int drain, int index) {
this.drain = drain;
this.index = index;
}
}
public static void main(String[] args) {
// Test Case 1
System.out.println("Test Case 1:");
int E1 = 6, N1 = 2;
int[] A1 = {1, 2};
int result1 = minExercisesToTired(E1, N1, A1);
System.out.println("Expected: 4, Got: " + result1);
// Test Case 2
System.out.println("\nTest Case 2:");
int E2 = 10, N2 = 2;
int[] A2 = {1, 2};
int result2 = minExercisesToTired(E2, N2, A2);
System.out.println("Expected: -1, Got: " + result2);
// Test Case 3
System.out.println("\nTest Case 3:");
int E3 = 2, N3 = 3;
int[] A3 = {1, 5, 2};
int result3 = minExercisesToTired(E3, N3, A3);
System.out.println("Expected: 1, Got: " + result3);
}
}
Key Differences and Features of the Java Implementation
- Created a static inner class
Exercise
to store both the energy drain value and original index, similar to how tuples were used in Python.
- Used Java's
Arrays.sort
with a custom comparator to sort exercises in descending order of energy drain.
Main Algorithm
- Sort exercises by energy drain (descending order).
- Try each exercise up to 2 times.
- Keep track of total energy drained and the number of exercises performed.
- Return early if the energy threshold is reached.
- Return
-1
if it is impossible to reach a tired state.
Test Cases and Expected Outputs
- Case 1: Returns
4
(using both exercises twice).
- Case 2: Returns
-1
(impossible to reach a tired state).
- Case 3: Returns
1
(using the 5-energy exercise once).
JavaScript Code:
/**
* Calculate minimum number of exercises needed to become tired.
* @param {number} E - Initial energy
* @param {number} N - Number of exercises
* @param {number[]} A - Array of energy drain values for each exercise
* @returns {number} Minimum number of exercises needed, or -1 if impossible
*/
function minExercisesToTired(E, N, A) {
// Create array of exercise objects with drain value and original index
const exercises = A.map((drain, index) => ({ drain, index }));
// Sort exercises by energy drain in descending order
exercises.sort((a, b) => b.drain - a.drain);
let totalEnergyPossible = 0;
let countExercises = 0;
// Try each exercise up to 2 times
for (const exercise of exercises) {
for (let i = 0; i < 2; i++) {
if (totalEnergyPossible < E) {
totalEnergyPossible += exercise.drain;
countExercises++;
// If we've reached or exceeded the energy threshold
if (totalEnergyPossible >= E) {
return countExercises;
}
}
}
}
// If we can't drain enough energy even using all exercises twice
return -1;
}
// Test cases
function runTestCases() {
console.log("Test Case 1:");
const E1 = 6, N1 = 2;
const A1 = [1, 2];
console.log(`Expected: 4, Got: ${minExercisesToTired(E1, N1, A1)}`);
console.log("\nTest Case 2:");
const E2 = 10, N2 = 2;
const A2 = [1, 2];
console.log(`Expected: -1, Got: ${minExercisesToTired(E2, N2, A2)}`);
console.log("\nTest Case 3:");
const E3 = 2, N3 = 3;
const A3 = [1, 5, 2];
console.log(`Expected: 1, Got: ${minExercisesToTired(E3, N3, A3)}`);
}
// Run the test cases when the page loads
window.onload = function() {
runTestCases();
};
JavaScript Exercise Calculator
Key Features of the JavaScript Implementation
Modern JavaScript Features:
Array.map()
to create exercise objects
- Template literals for string interpolation
const
/let
for proper variable scoping
for...of
loop for array iteration
Data Structure Changes:
- Used plain objects instead of a class for exercise data
- Used
Array.map()
to create the array of exercise objects
Core Algorithm:
- Sort exercises by energy drain (descending)
- Try each exercise up to 2 times
- Track total energy drained and exercises performed
- Return early if the energy threshold is reached
- Return
-1
if impossible to reach a tired state
Added Features:
- JSDoc comments for better documentation and IDE support
Test Cases:
- Case 1: Returns
4
(using both exercises twice)
- Case 2: Returns
-1
(impossible to reach a tired state)
- Case 3: Returns
1
(using the 5-energy exercise once)
C++ Code:
#include
#include
#include
using namespace std;
// Structure to store exercise information
struct Exercise {
int drain;
int index;
Exercise(int d, int i) : drain(d), index(i) {}
}
/**
* Calculate minimum number of exercises needed to become tired.
* @param E Initial energy
* @param N Number of exercises
* @param A Vector of energy drain values for each exercise
* @return Minimum number of exercises needed, or -1 if impossible
*/
int minExercisesToTired(int E, int N, vector& A) {
// Create vector of Exercise objects
vector exercises;
exercises.reserve(N);
for (int i = 0; i < N; i++) {
exercises.emplace_back(A[i], i);
}
// Sort exercises by energy drain in descending order
sort(exercises.begin(), exercises.end(),
[](const Exercise& a, const Exercise& b) {
return a.drain > b.drain;
});
int totalEnergyPossible = 0;
int countExercises = 0;
// Try each exercise up to 2 times
for (const Exercise& exercise : exercises) {
for (int i = 0; i < 2; i++) {
if (totalEnergyPossible < E) {
totalEnergyPossible += exercise.drain;
countExercises++;
// If we've reached or exceeded the energy threshold
if (totalEnergyPossible >= E) {
return countExercises;
}
}
}
}
return -1; // If we can't drain enough energy
}
// Function to run test cases
void runTestCases() {
cout << "Test Case 1:" << endl;
int E1 = 6, N1 = 2;
vector A1 = {1, 2};
int result1 = minExercisesToTired(E1, N1, A1);
cout << "Expected: 4, Got: " << result1 << endl;
cout << "\nTest Case 2:" << endl;
int E2 = 10, N2 = 2;
vector A2 = {1, 2};
int result2 = minExercisesToTired(E2, N2, A2);
cout << "Expected: -1, Got: " << result2 << endl;
cout << "\nTest Case 3:" << endl;
int E3 = 2, N3 = 3;
vector A3 = {1, 5, 2};
int result3 = minExercisesToTired(E3, N3, A3);
cout << "Expected: 1, Got: " << result3 << endl;
}
int main() {
runTestCases();
return 0;
}
C++ Code Key Features:
- Used modern C++ features:
- std::vector for dynamic arrays
- Range-based for loops
- Lambda functions for sorting
- struct for Exercise data
- vector.reserve() for performance optimization
- Key differences from other versions:
- Used struct instead of class for Exercise data
- Used reference parameters to avoid copying
- Used C++ STL algorithms (sort)
- Implemented proper memory management using vector
- The core algorithm remains the same:
- Sort exercises by energy drain (descending)
- Try each exercise up to 2 times
- Track total energy drained and exercises performed
- Return early if energy threshold is reached
- Return -1 if impossible to reach tired state
- The test cases demonstrate the same scenarios:
- Case 1: Returns 4 (using both exercises twice)
- Case 2: Returns -1 (impossible to reach tired state)
- Case 3: Returns 1 (using the 5-energy exercise once)
C Code:
#include <stdio.h>
#include <stdlib.h>
// Structure to store exercise information
typedef struct {
int drain;
int index;
} Exercise;
// Comparison function for qsort
int compare(const void* a, const void* b) {
Exercise* ex1 = (Exercise*)a;
Exercise* ex2 = (Exercise*)b;
return ex2->drain - ex1->drain; // Sort in descending order
}
/**
* Calculate minimum number of exercises needed to become tired.
* @param E Initial energy
* @param N Number of exercises
* @param A Array of energy drain values for each exercise
* @return Minimum number of exercises needed, or -1 if impossible
*/
int minExercisesToTired(int E, int N, int* A) {
// Allocate memory for exercises array
Exercise* exercises = (Exercise*)malloc(N * sizeof(Exercise));
if (exercises == NULL) {
printf("Memory allocation failed!\n");
return -1;
}
// Initialize exercises array
for (int i = 0; i < N; i++) {
exercises[i].drain = A[i];
exercises[i].index = i;
}
// Sort exercises by energy drain in descending order
qsort(exercises, N, sizeof(Exercise), compare);
int totalEnergyPossible = 0;
int countExercises = 0;
// Try each exercise up to 2 times
for (int i = 0; i < N; i++) {
// Can use each exercise up to 2 times
for (int j = 0; j < 2; j++) {
if (totalEnergyPossible < E) {
totalEnergyPossible += exercises[i].drain;
countExercises++;
// If we've reached or exceeded the energy threshold
if (totalEnergyPossible >= E) {
free(exercises); // Free allocated memory
return countExercises;
}
}
}
}
// Free allocated memory before returning
free(exercises);
// If we can't drain enough energy even using all exercises twice
return -1;
}
// Function to run test cases
void runTestCases() {
// Test Case 1
printf("Test Case 1:\n");
int E1 = 6, N1 = 2;
int A1[] = {1, 2};
int result1 = minExercisesToTired(E1, N1, A1);
printf("Expected: 4, Got: %d\n", result1);
// Test Case 2
printf("\nTest Case 2:\n");
int E2 = 10, N2 = 2;
int A2[] = {1, 2};
int result2 = minExercisesToTired(E2, N2, A2);
printf("Expected: -1, Got: %d\n", result2);
// Test Case 3
printf("\nTest Case 3:\n");
int E3 = 2, N3 = 3;
int A3[] = {1, 5, 2};
int result3 = minExercisesToTired(E3, N3, A3);
printf("Expected: 1, Got: %d\n", result3);
}
int main() {
runTestCases();
return 0;
}
Key Features and Differences in C Implementation:
Memory Management:
- Used
malloc()
for dynamic memory allocation.
- Properly freed memory using
free()
to prevent memory leaks.
- Added error checking for memory allocation.
Data Structures:
- Used a
struct
for Exercise data.
- Created
typedef
for easier struct
usage.
- Used arrays instead of vectors/lists.
Sorting:
- Implemented comparison function for
qsort
.
- Used standard library
qsort
instead of custom sorting.
qsort
function handles descending order comparison.
C-Specific Considerations:
- No built-in boolean type (used
int
).
- Manual pointer management.
- Traditional
for
loops instead of range-based loops.
printf
instead of cout
/console.log
.
The core algorithm remains the same and handles all test cases:
- Case 1: Returns 4 (using both exercises twice).
- Case 2: Returns -1 (impossible to reach tired state).
- Case 3: Returns 1 (using the 5-energy exercise once).
 |
Infosys HackWithInfy 20205
|
|