Number of ways such that only K bars are visible from the left

Given a number K, and N bars of height from 1 to N, the task is to find the number of ways to arrange the N bars such that only K bars are visible from the left.
Examples:Â
Input: N=4, K=3
Output:
6
Explanation: The 6 permutations where only 3 bars are visible from the left are:
- 1 2 4 3
- 1 3 2 4
- 1 3 4 2
- 2 1 3 4
- 2 3 1 4
- 2 3 4 1
The Underlined bars are not visible.
Input: N=5, K=2
Output:
50
Naive Approach: The naive approach would be to check all permutations of 1 to N and check whether the number of bars visible from the left is K or not.Â
Below is the implementation of the above approach:
C++
// C++ program for the above approach#include <bits/stdc++.h>using namespace std;Â
// Function to calculate the number// of bars that are visible from// the left for a particular arrangementint noOfbarsVisibleFromLeft(vector<int> v){Â Â Â Â int last = 0, ans = 0;Â Â Â Â for (auto u : v)Â
        // If current element is greater// than the last greater element,// it is visible        if (last < u) {            ans++;            last = u;        }    return ans;}Â
// Function to calculate the number// of rearrangements where// K bars are visible from the leftint KvisibleFromLeft(int N, int K){    // Vector to store current permutation    vector<int> v(N);    for (int i = 0; i < N; i++)        v[i] = i + 1;    int ans = 0;Â
    // Check for all permutations    do {Â
        // If current permutation meets// the conditions, increment answer        if (noOfbarsVisibleFromLeft(v) == K)            ans++;    } while (next_permutation(v.begin(), v.end()));Â
    return ans;}Â
// Driver codeint main(){    // Input    int N = 5, K = 2;Â
    // Function call    cout << KvisibleFromLeft(N, K) << endl;Â
    return 0;} |
Java
// Java program for above approachimport java.util.*;Â
public class Solution {Â
  // Function to calculate the number  // of bars that are visible from  // the left for a particular arrangement  static int noOfbarsVisibleFromLeft(int[] v)  {    int last = 0, ans = 0;    for (int u : v)Â
      // If current element is greater      // than the last greater element,      // it is visible      if (last < u) {        ans++;        last = u;      }    return ans;  }     // Function to generate next permutation of array  static void NextPermutation(int[] nums)  {         // Starting from the end, look for the first index    // that is not in descending order    var startIndex = nums.length - 2;Â
    while (startIndex >= 0)    {             // Find first decreasing element      if (nums[startIndex] < nums[startIndex + 1]) {        break;      }      --startIndex;    }Â
    if (startIndex >= 0)     {             // Starting from the end, look for the first      // element greater than the start index      int endIndex = nums.length - 1;Â
      while (endIndex > startIndex)       {                 // Find first greater element        if (nums[endIndex] > nums[startIndex]) {          break;        }        --endIndex;      }Â
      // Swap first and last elements      int t = nums[startIndex];      nums[startIndex] = nums[endIndex];      nums[endIndex] = t;    }Â
    // Reverse the array    Reverse(nums, startIndex + 1);  }Â
  static void Reverse(int[] nums, int startIndex)  {    for (int start = startIndex, end = nums.length - 1;         start < end; ++start, --end) {      int t = nums[start];      nums[start] = nums[end];      nums[end] = t;    }  }Â
  // Function to calculate the number  // of rearrangements where  // K bars are visible from the left  static int KvisibleFromLeft(int N, int K)  {         // Vector to store current permutation    int[] v = new int[N];    for (int i = 0; i < N; i++) {      v[i] = i + 1;    }    int ans = 0;Â
    int count = 1;    for (int i = 1; i <= N; i++) {      count *= i;    }Â
    // Check for all permutations    for (int i = 0; i < count; i++) {      if (noOfbarsVisibleFromLeft(v) == K) {        ans++;      }      NextPermutation(v);    }    return ans;  }Â
  // Driver Code  public static void main(String[] args)  {    // Input    int N = 5, K = 2;Â
    // Function call    System.out.println(KvisibleFromLeft(N, K));  }}Â
// This code is contributed by karandeep1234. |
Python3
# Python3 program for the above approachÂ
# Function to calculate the number# of bars that are visible from# the left for a particular arrangementdef noOfbarsVisibleFromLeft(v):Â Â Â Â last = 0Â Â Â Â ans = 0Â
    for u in v:    # If current element is greater    # than the last greater element,    # it is visible        if (last < u):            ans += 1            last = uÂ
    return ansÂ
def nextPermutation(nums):    i = len(nums) - 2    while i > -1:        if nums[i] < nums[i + 1]:            j = len(nums) - 1            while j > i:                if nums[j] > nums[i]:                    break                j -= 1            nums[i], nums[j] = nums[j], nums[i]            break        i -= 1    nums[i + 1:] = reversed(nums[i + 1:])    return nums   # Function to calculate the number# of rearrangements where# K bars are visible from the leftdef KvisibleFromLeft(N, K):    # Vector to store current permutation    v = [0]*(N)    for i in range(N):        v[i] = i + 1    ans = 0Â
    temp = list(v)Â
    # Check for all permutations    while True:        # If current permutation meets# the conditions, increment answer        if (noOfbarsVisibleFromLeft(v) == K):            ans += 1        v = nextPermutation(v)Â
        if v == temp:            breakÂ
    return ansÂ
# Driver codeif __name__ == '__main__':    # Input    N = 5    K = 2Â
    # Function call    print (KvisibleFromLeft(N, K))Â
# This code is contributed by mohit kumar 29. |
C#
// C# program to implement above approachusing System;using System.Collections.Generic;Â
class GFG{Â
    // Function to calculate the number    // of bars that are visible from    // the left for a particular arrangement    static int noOfbarsVisibleFromLeft(int[] v)    {        int last = 0, ans = 0;        foreach (var u in v){Â
            // If current element is greater            // than the last greater element,            // it is visible            if (last < u) {                ans++;                last = u;            }        }        return ans;    }Â
    // Function to generate next permutation of array    public static void NextPermutation(int[] nums) {        // Starting from the end, look for the first index that is not in descending order        var startIndex = nums.Length - 2;          while (startIndex >= 0) {            // Find first decreasing element            if (nums[startIndex] < nums[startIndex + 1]) {                break;            }            --startIndex;        }          if (startIndex >= 0) {            // Starting from the end, look for the first element greater than the start index            int endIndex = nums.Length - 1;              while (endIndex > startIndex) {                // Find first greater element                if (nums[endIndex] > nums[startIndex]) {                    break;                }                --endIndex;            }              // Swap first and last elements            Swap(ref nums[startIndex], ref nums[endIndex]);        }          // Reverse the array        Reverse(nums, startIndex + 1);    }      static void Reverse(int[] nums, int startIndex) {        for (int start = startIndex, end = nums.Length - 1; start < end; ++start, --end) {            Swap(ref nums[start], ref nums[end]);        }    }      static void Swap(ref int a, ref int b) {        var tmp = a;        a = b;        b = tmp;    }Â
    // Function to calculate the number    // of rearrangements where    // K bars are visible from the left    static int KvisibleFromLeft(int N, int K)    {        // Vector to store current permutation        int[] v = new int[N];        for (int i = 0 ; i < N ; i++){            v[i] = i + 1;        }        int ans = 0;Â
        int count = 1;        for(int i = 1 ; i <= N ; i++){            count *= i;        }Â
        // Check for all permutations        for(int i = 0 ; i < count ; i++){            if (noOfbarsVisibleFromLeft(v) == K){                ans++;            }            NextPermutation(v);        }Â
        return ans;    }Â
Â
    // Driver Code    public static void Main(string[] args){                 // Input        int N = 5, K = 2;Â
        // Function call        Console.Write(KvisibleFromLeft(N, K) + "\n");Â
    }}Â
// This code is contributed by subhamgoyal2014. |
Javascript
function swap(nums, i, j) {        let temp = nums[i];        nums[i] = nums[j];        nums[j] = temp;    }  function reverse(nums, start) {        let i = start, j = nums.length - 1;        while (i < j) {            swap(nums, i, j);            i++;            j--;        }    } // function to find next greater permutationfunction nextPermutation(nums) {        let i = nums.length - 2;        while (i >= 0 && nums[i + 1] <= nums[i]) {            i--;        }        let flag= false;        if (i >= 0) {            let j = nums.length - 1;            while (nums[j] <= nums[i]) {                j--;            }            swap(nums, i, j);            flag = true;        }        reverse(nums,i+1);       return flag;    }Â
// Function to calculate the number// of bars that are visible from// the left for a particular arrangementfunction noOfbarsVisibleFromLeft(v){Â Â Â Â let last = 0, ans = 0;Â Â Â Â for (let i=0;i< v.length;i++)Â
        // If current element is greater// than the last greater element,// it is visible        if (last < v[i]) {            ans++;            last = v[i];        }    return ans;}Â
// Function to calculate the number// of rearrangements where// K bars are visible from the leftfunction KvisibleFromLeft(N, K){    // Vector to store current permutation    let v=[];    for (let i = 0; i < N; i++)        v.push(i + 1);    let ans = 0;Â
    // Check for all permutations    do {        // If current permutation meets// the conditions, increment answer        if (noOfbarsVisibleFromLeft(v) == K)             ans++;    } while (nextPermutation(v)==true);Â
    return ans;}Â
// Driver codeÂ
    // Input    let N = 5, K = 2;Â
    // Function call    console.log( KvisibleFromLeft(N, K) );Â
// This code is contributed by garg28harsh. |
50
Time Complexity: O(N!)
Auxiliary Space: O(N)
Efficient Approach: The efficient approach would be to use recursion. Follow the steps below to solve the problem:Â
- Create a recursive function KvisibleFromLeft() that takes N and K as input parameters and does the following:
- Base cases:
- If N is equal to K, there is one way to arrange the bars, which is in ascending order. So, return 1.
- If K==1, there are (N-1)! ways to arrange the bars, as the longest bar is placed in the first position and the remaining N-1 bars can be placed anywhere on the remaining N-1 positions. So, return (N-1)!.
- For the recursion, there are two cases:
- The smallest bar can be placed at the first position, then, among the remaining N-1 bars, only K-1 bars need to be visible. Thus, the answer would be the same as the number of ways to arrange N-1 bars such that K-1 bars are visible. This case, thus, recursively calls KvisibleFromLeft(N-1, K-1).
- The smallest bar can be placed at any of the N-1 positions, other than the first. This would hide the smallest bar, and thus, the answer would be the same as the number of ways to arrange N-1 bars such that K bars are visible. Thus, this case recursively calls (N-1)*KvisibleFromLeft(N-1,K).
- Base cases:
Below is the implementation of the above approach:Â
C++
// C++ implementation for the above approach#include <bits/stdc++.h>using namespace std;Â
// Function to calculate the number of permutations of// N, where only K bars are visible from the left.int KvisibleFromLeft(int N, int K){Â
    // Only ascending order is possible    if (N == K)        return 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1) {        int ans = 1;        for (int i = 1; i < N; i++)            ans *= i;        return ans;    }Â
    // Recursing    return KvisibleFromLeft(N - 1, K - 1)           + (N - 1) * KvisibleFromLeft(N - 1, K);}// Driver codeint main(){    // Input    int N = 5, K = 2;Â
    // Function call    cout << KvisibleFromLeft(N, K) << endl;    return 0;} |
Java
// Java program for the above approachclass GFG{Â
// Function to calculate the number of // permutations of N, where only K bars// are visible from the left.static int KvisibleFromLeft(int N, int K){         // Only ascending order is possible    if (N == K)        return 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1)    {        int ans = 1;        for(int i = 1; i < N; i++)            ans *= i;                     return ans;    }Â
    // Recursing    return KvisibleFromLeft(N - 1, K - 1) +         (N - 1) * KvisibleFromLeft(N - 1, K);}Â
// Driver codepublic static void main(String[] args){         // Input    int N = 5, K = 2;Â
    // Function call    System.out.println(KvisibleFromLeft(N, K));}}Â
// This code is contributed by abhinavjain194 |
Python3
# Python 3 implementation for the above approachÂ
# Function to calculate the number of permutations of# N, where only K bars are visible from the left.def KvisibleFromLeft(N, K):       # Only ascending order is possible    if (N == K):        return 1Â
    # N is placed at the first position    # The nest N-1 are arranged in (N-1)! ways    if (K == 1):        ans = 1        for i in range(1, N, 1):            ans *= i        return ansÂ
    # Recursing    return KvisibleFromLeft(N - 1, K - 1) + (N - 1) * KvisibleFromLeft(N - 1, K)Â
# Driver codeif __name__ == '__main__':       # Input    N = 5    K = 2Â
    # Function call    print(KvisibleFromLeft(N, K))         # This code is contributed by ipg2016107. |
C#
// C# program for the above approachusing System;Â
class GFG{Â
// Function to calculate the number of // permutations of N, where only K bars// are visible from the left.static int KvisibleFromLeft(int N, int K){         // Only ascending order is possible    if (N == K)        return 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1)    {        int ans = 1;        for(int i = 1; i < N; i++)            ans *= i;                     return ans;    }Â
    // Recursing    return KvisibleFromLeft(N - 1, K - 1) +         (N - 1) * KvisibleFromLeft(N - 1, K);}Â
// Driver codepublic static void Main(String[] args){         // Input    int N = 5, K = 2;Â
    // Function call    Console.Write(KvisibleFromLeft(N, K));}}Â
// This code is contributed by shivanisinghss2110 |
Javascript
<script>// Javascript implementation for the above approachÂ
Â
// Function to calculate the number of permutations of// N, where only K bars are visible from the left.function KvisibleFromLeft(N, K) {Â
    // Only ascending order is possible    if (N == K)        return 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1) {        let ans = 1;        for (let i = 1; i < N; i++)            ans *= i;        return ans;    }Â
    // Recursing    return KvisibleFromLeft(N - 1, K - 1)        + (N - 1) * KvisibleFromLeft(N - 1, K);}// Driver codeÂ
// Inputlet N = 5, K = 2;Â
// Function calldocument.write(KvisibleFromLeft(N, K) + "<br>");Â
// This code is contributed by gfgking.</script> |
50
Time Complexity: O(2N)
Auxiliary Space: O(1)
Efficient Approach: The above recursion can be memoized and thus, dynamic programming can be used as there are optimal substructures.
Below is the implementation of the above approach:Â
C++
// C++ implementation for the above approach#include <bits/stdc++.h>using namespace std;Â
// dp arrayint dp[1005][1005];Â
// Function to calculate the number// of permutations of N, where// only K bars are visible from the left.int KvisibleFromLeft(int N, int K){    // If subproblem has already// been calculated, return    if (dp[N][K] != -1)        return dp[N][K];Â
    // Only ascending order is possible    if (N == K)        return dp[N][K] = 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1) {        int ans = 1;        for (int i = 1; i < N; i++)            ans *= i;        return dp[N][K] = ans;    }Â
    // Recursing    return dp[N][K]           = KvisibleFromLeft(N - 1, K - 1)             + (N - 1) * KvisibleFromLeft(N - 1, K);}// Driver codeint main(){    // Input    int N = 5, K = 2;Â
    // Initialize dp array    memset(dp, -1, sizeof(dp));Â
    // Function call    cout << KvisibleFromLeft(N, K) << endl;    return 0;} |
Java
// Java implementation for the above approachimport java.util.*;Â
class GFG{Â
// dp arraystatic int [][]dp = new int[1005][1005];Â
// Function to calculate the number// of permutations of N, where// only K bars are visible from the left.static int KvisibleFromLeft(int N, int K){    // If subproblem has already// been calculated, return    if (dp[N][K] != -1)        return dp[N][K];Â
    // Only ascending order is possible    if (N == K)        return dp[N][K] = 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1) {        int ans = 1;        for (int i = 1; i < N; i++)            ans *= i;        return dp[N][K] = ans;    }Â
    // Recursing    return dp[N][K]           = KvisibleFromLeft(N - 1, K - 1)             + (N - 1) * KvisibleFromLeft(N - 1, K);}// Driver codepublic static void main(String[] args){    // Input    int N = 5, K = 2;Â
    // Initialize dp array    for(int i = 0; i < 1005; i++)  {    for (int j = 0; j < 1005; j++)    {      dp[i][j] = -1;    }  }      // Function call    System.out.print( KvisibleFromLeft(N, K));}}Â
// This code is contributed by shivanisinghss2110 |
Python3
# Python3 implementation for the above approachÂ
# dp arraydp = [[0 for i in range(1005)] for j in range(1005)]  # Function to calculate the number# of permutations of N, where# only K bars are visible from the left.def KvisibleFromLeft(N, K):       # If subproblem has already    # been calculated, return    if (dp[N][K] != -1):        return dp[N][K]      # Only ascending order is possible    if (N == K):        dp[N][K] = 1        return dp[N][K]      # N is placed at the first position    # The nest N-1 are arranged in (N-1)! ways    if (K == 1):        ans = 1        for i in range(1, N):            ans *= i        dp[N][K] = ans        return dp[N][K]      # Recursing    dp[N][K] = KvisibleFromLeft(N - 1, K - 1) + (N - 1) * KvisibleFromLeft(N - 1, K)    return dp[N][K]Â
# InputN, K = 5, 2Â
# Initialize dp arrayfor i in range(1005):Â Â Â Â for j in range(1005):Â Â Â Â Â Â Â Â dp[i][j] = -1Â
# Function callprint( KvisibleFromLeft(N, K))Â
# This code is contributed by divyeshrabadiya07. |
C#
// C# implementation for the above approachusing System;Â
public class GFG{Â
// dp arraystatic int [,]dp = new int[1005, 1005];Â
// Function to calculate the number// of permutations of N, where// only K bars are visible from the left.static int KvisibleFromLeft(int N, int K){    // If subproblem has already// been calculated, return    if (dp[N ,K] != -1)        return dp[N,K];Â
    // Only ascending order is possible    if (N == K)        return dp[N,K] = 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1) {        int ans = 1;        for (int i = 1; i < N; i++)            ans *= i;        return dp[N,K] = ans;    }Â
    // Recursing    return dp[N,K]           = KvisibleFromLeft(N - 1, K - 1)             + (N - 1) * KvisibleFromLeft(N - 1, K);}// Driver codepublic static void Main(String[] args){    // Input    int N = 5, K = 2;Â
    // Initialize dp array    for(int i = 0; i < 1005; i++)  {    for (int j = 0; j < 1005; j++)    {      dp[i, j] = -1;    }  }      // Function call    Console.Write( KvisibleFromLeft(N, K));}}Â
// This code is contributed by shivanisinghss2110 |
Javascript
<script>Â
// Javascript implementation for // the above approachÂ
// dp arraylet dp = new Array(1005).fill(0).map(Â Â Â () => new Array(1005).fill(-1));Â
// Function to calculate the number// of permutations of N, where// only K bars are visible from the left.function KvisibleFromLeft(N, K) {         // If subproblem has already    // been calculated, return    if (dp[N][K] != -1)        return dp[N][K];Â
    // Only ascending order is possible    if (N == K)        return dp[N][K] = 1;Â
    // N is placed at the first position    // The nest N-1 are arranged in (N-1)! ways    if (K == 1)     {        let ans = 1;                 for(let i = 1; i < N; i++)            ans *= i;                     return dp[N][K] = ans;    }Â
    // Recursing    return dp[N][K] = KvisibleFromLeft(N - 1, K - 1) +             (N - 1) * KvisibleFromLeft(N - 1, K);}Â
// Driver codeÂ
// Inputlet N = 5, K = 2;Â
// Function calldocument.write(KvisibleFromLeft(N, K) + "<br>")Â
// This code is contributed by _saurabh_jaiswalÂ
</script> |
50
Time Complexity: O(NK)
Auxiliary Space: O(NK)
Â
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 zambiatek!



