Auxiliary Given a pattern containing only I’s and D’s. I for increasing and D for decreasing. Device an algorithm to print the minimum number following that pattern. Digits from 1-9 and digits can’t repeat.
Examples:
Input: D Output: 21
Input: I Output: 12
Input: DD Output: 321
Input: II Output: 123
Input: DIDI Output: 21435
Input: IIDDD Output: 126543
Input: DDIDDIID Output: 321654798
Source: Amazon Interview Question
Below are some important observations
Since digits can’t repeat, there can be at most 9 digits in output.
Also, number of digits in output is one more than number of characters in input. Note that the first character of input corresponds to two digits in output.
Idea is to iterate over input array and keep track of last printed digit and maximum digit printed so far.
Steps were to follow to solve this problem:
- Create a static function named “PrintMinNumberForPattern” that takes a string array arr as input.
- Create two variables “curr_max” and “last_entry” and initialize them to 0.
- Traverse through the input array arr using a for a loop.
- Create a variable “noOfNextD” and initialize it to 0.
- If the character at index i is ‘I’, perform the following steps:
- Find the number of next consecutive D’s available by iterating over the array from the next index until a non-‘D’ character is encountered.
- If i is 0, set curr_max to noOfNextD+2 and print the incremented sequence from 1.
- If i is not 0, set curr_max to curr_max + noOfNextD + 1 and print the digit for ‘I’.
- For all next consecutive ‘D’ characters, print the decremented sequence.
- If the character at index i is ‘D’, perform the following steps:
- If i is 0, find the number of the next consecutive ‘D’ characters available and set curr_max to noOfNextD+2. Print the first two digits (curr_max and curr_max-1).
- If i is not 0, print the decremented value of last_entry.
- Print a newline character after the for loop completes.
Below is the implementation of the above idea:
C++
#include <bits/stdc++.h>
using namespace std;
void PrintMinNumberForPattern(string arr)
{
int curr_max = 0;
int last_entry = 0;
int j;
for ( int i=0; i<arr.length(); i++)
{
int noOfNextD = 0;
switch (arr[i])
{
case 'I' :
j = i+1;
while (arr[j] == 'D' && j < arr.length())
{
noOfNextD++;
j++;
}
if (i==0)
{
curr_max = noOfNextD + 2;
cout << " " << ++last_entry;
cout << " " << curr_max;
last_entry = curr_max;
}
else
{
curr_max = curr_max + noOfNextD + 1;
last_entry = curr_max;
cout << " " << last_entry;
}
for ( int k=0; k<noOfNextD; k++)
{
cout << " " << --last_entry;
i++;
}
break ;
case 'D' :
if (i == 0)
{
j = i+1;
while (arr[j] == 'D' && j < arr.length())
{
noOfNextD++;
j++;
}
curr_max = noOfNextD + 2;
cout << " " << curr_max << " " << curr_max - 1;
last_entry = curr_max - 1;
}
else
{
cout << " " << last_entry - 1;
last_entry--;
}
break ;
}
}
cout << endl;
}
int main()
{
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
return 0;
}
|
Java
class GFG
{
static void PrintMinNumberForPattern(String arr)
{
int curr_max = 0 ;
int last_entry = 0 ;
int j;
for ( int i = 0 ; i < arr.length(); i++)
{
int noOfNextD = 0 ;
switch (arr.charAt(i))
{
case 'I' :
j = i + 1 ;
while (j < arr.length() && arr.charAt(j) == 'D' )
{
noOfNextD++;
j++;
}
if (i == 0 )
{
curr_max = noOfNextD + 2 ;
System.out.print( " " + ++last_entry);
System.out.print( " " + curr_max);
last_entry = curr_max;
}
else
{
curr_max = curr_max + noOfNextD + 1 ;
last_entry = curr_max;
System.out.print( " " + last_entry);
}
for ( int k = 0 ; k < noOfNextD; k++)
{
System.out.print( " " + --last_entry);
i++;
}
break ;
case 'D' :
if (i == 0 )
{
j = i + 1 ;
while (j < arr.length()&&arr.charAt(j) == 'D' )
{
noOfNextD++;
j++;
}
curr_max = noOfNextD + 2 ;
System.out.print( " " + curr_max + " " + (curr_max - 1 ));
last_entry = curr_max - 1 ;
}
else
{
System.out.print( " " + (last_entry - 1 ));
last_entry--;
}
break ;
}
}
System.out.println();
}
public static void main(String[] args)
{
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
}
}
|
Python3
def PrintMinNumberForPattern(arr):
curr_max = 0
last_entry = 0
i = 0
while i < len (arr):
noOfNextD = 0
if arr[i] = = "I" :
j = i + 1
while j < len (arr) and arr[j] = = "D" :
noOfNextD + = 1
j + = 1
if i = = 0 :
curr_max = noOfNextD + 2
last_entry + = 1
print (" ", last_entry, end = " ")
print (" ", curr_max, end = " ")
last_entry = curr_max
else :
curr_max + = noOfNextD + 1
last_entry = curr_max
print (" ", last_entry, end = " ")
for k in range (noOfNextD):
last_entry - = 1
print (" ", last_entry, end = " ")
i + = 1
elif arr[i] = = "D" :
if i = = 0 :
j = i + 1
while j < len (arr) and arr[j] = = "D" :
noOfNextD + = 1
j + = 1
curr_max = noOfNextD + 2
print (" ", curr_max, curr_max - 1, end = " ")
last_entry = curr_max - 1
else :
print (" ", last_entry - 1, end = " ")
last_entry - = 1
i + = 1
print ()
if __name__ = = "__main__" :
PrintMinNumberForPattern( "IDID" )
PrintMinNumberForPattern( "I" )
PrintMinNumberForPattern( "DD" )
PrintMinNumberForPattern( "II" )
PrintMinNumberForPattern( "DIDI" )
PrintMinNumberForPattern( "IIDDD" )
PrintMinNumberForPattern( "DDIDDIID" )
|
C#
using System;
class GFG
{
static void PrintMinNumberForPattern(String arr)
{
int curr_max = 0;
int last_entry = 0;
int j;
for ( int i = 0; i < arr.Length; i++)
{
int noOfNextD = 0;
switch (arr[i])
{
case 'I' :
j = i + 1;
while (j < arr.Length && arr[j] == 'D' )
{
noOfNextD++;
j++;
}
if (i == 0)
{
curr_max = noOfNextD + 2;
Console.Write( " " + ++last_entry);
Console.Write( " " + curr_max);
last_entry = curr_max;
}
else
{
curr_max = curr_max + noOfNextD + 1;
last_entry = curr_max;
Console.Write( " " + last_entry);
}
for ( int k = 0; k < noOfNextD; k++)
{
Console.Write( " " + --last_entry);
i++;
}
break ;
case 'D' :
if (i == 0)
{
j = i + 1;
while (j < arr.Length&&arr[j] == 'D' )
{
noOfNextD++;
j++;
}
curr_max = noOfNextD + 2;
Console.Write( " " + curr_max + " " + (curr_max - 1));
last_entry = curr_max - 1;
}
else
{
Console.Write( " " + (last_entry - 1));
last_entry--;
}
break ;
}
}
Console.WriteLine();
}
public static void Main(String[] args)
{
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
}
}
|
PHP
<?php
function PrintMinNumberForPattern( $arr )
{
$curr_max = 0;
$last_entry = 0;
$j ;
for ( $i = 0; $i < strlen ( $arr ); $i ++)
{
$noOfNextD = 0;
switch ( $arr [ $i ])
{
case 'I' :
$j = $i + 1;
while ( $arr [ $j ] == 'D' &&
$j < strlen ( $arr ))
{
$noOfNextD ++;
$j ++;
}
if ( $i == 0)
{
$curr_max = $noOfNextD + 2;
echo " " , ++ $last_entry ;
echo " " , $curr_max ;
$last_entry = $curr_max ;
}
else
{
$curr_max = $curr_max +
$noOfNextD + 1;
$last_entry = $curr_max ;
echo " " , $last_entry ;
}
for ( $k = 0; $k < $noOfNextD ; $k ++)
{
echo " " , -- $last_entry ;
$i ++;
}
break ;
case 'D' :
if ( $i == 0)
{
$j = $i +1;
while (( $arr [ $j ] == 'D' ) &&
( $j < strlen ( $arr )))
{
$noOfNextD ++;
$j ++;
}
$curr_max = $noOfNextD + 2;
echo " " , $curr_max ,
" " , $curr_max - 1;
$last_entry = $curr_max - 1;
}
else
{
echo " " , $last_entry - 1;
$last_entry --;
}
break ;
}
}
echo "\n" ;
}
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
?>
|
Javascript
<script>
function PrintMinNumberForPattern(arr)
{
let curr_max = 0;
let last_entry = 0;
let j;
for (let i = 0; i < arr.length; i++)
{
let noOfNextD = 0;
switch (arr[i])
{
case 'I' :
j = i + 1;
while (j < arr.length && arr[j] == 'D ')
{
noOfNextD++;
j++;
}
if (i == 0)
{
curr_max = noOfNextD + 2;
// If ' I ' is first letter, print incremented
// sequence from 1
document.write(" " + ++last_entry);
document.write(" " + curr_max);
// Set max digit reached
last_entry = curr_max;
}
else
{
// If not first letter
// Get next digit to print
curr_max = curr_max + noOfNextD + 1;
// Print digit for I
last_entry = curr_max;
document.write(" " + last_entry);
}
// For all next consecutive ' D ' print
// decremented sequence
for (let k = 0; k < noOfNextD; k++)
{
document.write(" " + --last_entry);
i++;
}
break;
// If letter is ' D '
case ' D ':
if (i == 0)
{
// If ' D ' is first letter in sequence
// Find number of Next D' s available
j = i + 1;
while (j < arr.length && arr[j] == 'D' )
{
noOfNextD++;
j++;
}
curr_max = noOfNextD + 2;
document.write( " " + curr_max + " " + (curr_max - 1));
last_entry = curr_max - 1;
}
else
{
document.write( " " + (last_entry - 1));
last_entry--;
}
break ;
}
}
document.write( "<br>" );
}
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
</script>
|
Output 1 3 2 5 4
1 2
3 2 1
1 2 3
2 1 4 3 5
1 2 6 5 4 3
3 2 1 6 5 4 7 9 8
Time Complexity: O(N^2), overall time complexity. Where, N is the length of the string.
Auxiliary Space: O(1).
This solution is suggested by Swapnil Trambake.
Alternate Solution:
Let’s observe a few facts in case of a minimum number:
- The digits can’t repeat hence there can be 9 digits at most in output.
- To form a minimum number , at every index of the output, we are interested in the minimum number which can be placed at that index.
The idea is to iterate over the entire input array , keeping track of the minimum number (1-9) which can be placed at that position of the output.
The tricky part of course occurs when ‘D’ is encountered at index other than 0. In such a case we have to track the nearest ‘I’ to the left of ‘D’ and increment each number in the output vector by 1 in between ‘I’ and ‘D’.
We cover the base case as follows:
- If the first character of input is ‘I’ then we append 1 and 2 in the output vector and the minimum available number is set to 3 .The index of most recent ‘I’ is set to 1.
- If the first character of input is ‘D’ then we append 2 and 1 in the output vector and the minimum available number is set to 3, and the index of most recent ‘I’ is set to 0.
Now we iterate the input string from index 1 till its end and:
- If the character scanned is ‘I’ , a minimum value that has not been used yet is appended to the output vector .We increment the value of minimum no. available and index of most recent ‘I’ is also updated.
- If the character scanned is ‘D’ at index i of input array, we append the ith element from output vector in the output and track the nearest ‘I’ to the left of ‘D’ and increment each number in the output vector by 1 in between ‘I’ and ‘D’.
Following is the program for the same:
C++
#include<bits/stdc++.h>
using namespace std;
void printLeast(string arr)
{
int min_avail = 1, pos_of_I = 0;
vector< int >v;
if (arr[0]== 'I' )
{
v.push_back(1);
v.push_back(2);
min_avail = 3;
pos_of_I = 1;
}
else
{
v.push_back(2);
v.push_back(1);
min_avail = 3;
pos_of_I = 0;
}
for ( int i=1; i<arr.length(); i++)
{
if (arr[i]== 'I' )
{
v.push_back(min_avail);
min_avail++;
pos_of_I = i+1;
}
else
{
v.push_back(v[i]);
for ( int j=pos_of_I; j<=i; j++)
v[j]++;
min_avail++;
}
}
for ( int i=0; i<v.size(); i++)
cout << v[i] << " " ;
cout << endl;
}
int main()
{
printLeast( "IDID" );
printLeast( "I" );
printLeast( "DD" );
printLeast( "II" );
printLeast( "DIDI" );
printLeast( "IIDDD" );
printLeast( "DDIDDIID" );
return 0;
}
|
Java
import java.io.*;
import java.util.*;
public class GFG {
static void printLeast(String arr)
{
int min_avail = 1 , pos_of_I = 0 ;
ArrayList<Integer> al = new ArrayList<>();
if (arr.charAt( 0 ) == 'I' )
{
al.add( 1 );
al.add( 2 );
min_avail = 3 ;
pos_of_I = 1 ;
}
else
{
al.add( 2 );
al.add( 1 );
min_avail = 3 ;
pos_of_I = 0 ;
}
for ( int i = 1 ; i < arr.length(); i++)
{
if (arr.charAt(i) == 'I' )
{
al.add(min_avail);
min_avail++;
pos_of_I = i + 1 ;
}
else
{
al.add(al.get(i));
for ( int j = pos_of_I; j <= i; j++)
al.set(j, al.get(j) + 1 );
min_avail++;
}
}
for ( int i = 0 ; i < al.size(); i++)
System.out.print(al.get(i) + " " );
System.out.println();
}
public static void main(String args[])
{
printLeast( "IDID" );
printLeast( "I" );
printLeast( "DD" );
printLeast( "II" );
printLeast( "DIDI" );
printLeast( "IIDDD" );
printLeast( "DDIDDIID" );
}
}
|
Python3
def printLeast(arr):
min_avail = 1
pos_of_I = 0
v = []
if (arr[ 0 ] = = 'I' ):
v.append( 1 )
v.append( 2 )
min_avail = 3
pos_of_I = 1
else :
v.append( 2 )
v.append( 1 )
min_avail = 3
pos_of_I = 0
for i in range ( 1 , len (arr)):
if (arr[i] = = 'I' ):
v.append(min_avail)
min_avail + = 1
pos_of_I = i + 1
else :
v.append(v[i])
for j in range (pos_of_I, i + 1 ):
v[j] + = 1
min_avail + = 1
print ( * v, sep = ' ' )
printLeast( "IDID" )
printLeast( "I" )
printLeast( "DD" )
printLeast( "II" )
printLeast( "DIDI" )
printLeast( "IIDDD" )
printLeast( "DDIDDIID" )
|
C#
using System;
using System.Collections.Generic;
class GFG
{
static void printLeast(String arr)
{
int min_avail = 1, pos_of_I = 0;
List< int > al = new List< int >();
if (arr[0] == 'I' )
{
al.Add(1);
al.Add(2);
min_avail = 3;
pos_of_I = 1;
}
else
{
al.Add(2);
al.Add(1);
min_avail = 3;
pos_of_I = 0;
}
for ( int i = 1; i < arr.Length; i++)
{
if (arr[i] == 'I' )
{
al.Add(min_avail);
min_avail++;
pos_of_I = i + 1;
}
else
{
al.Add(al[i]);
for ( int j = pos_of_I; j <= i; j++)
al[j] = al[j] + 1;
min_avail++;
}
}
for ( int i = 0; i < al.Count; i++)
Console.Write(al[i] + " " );
Console.WriteLine();
}
public static void Main(String []args)
{
printLeast( "IDID" );
printLeast( "I" );
printLeast( "DD" );
printLeast( "II" );
printLeast( "DIDI" );
printLeast( "IIDDD" );
printLeast( "DDIDDIID" );
}
}
|
Javascript
<script>
function printLeast(arr)
{
let min_avail = 1, pos_of_I = 0;
let al = [];
if (arr[0] == 'I' )
{
al.push(1);
al.push(2);
min_avail = 3;
pos_of_I = 1;
}
else
{
al.push(2);
al.push(1);
min_avail = 3;
pos_of_I = 0;
}
for (let i = 1; i < arr.length; i++)
{
if (arr[i] == 'I' )
{
al.push(min_avail);
min_avail++;
pos_of_I = i + 1;
}
else
{
al.push(al[i]);
for (let j = pos_of_I; j <= i; j++)
al[j] = al[j] + 1;
min_avail++;
}
}
for (let i = 0; i < al.length; i++)
document.write(al[i] + " " );
document.write( "</br>" );
}
printLeast( "IDID" );
printLeast( "I" );
printLeast( "DD" );
printLeast( "II" );
printLeast( "DIDI" );
printLeast( "IIDDD" );
printLeast( "DDIDDIID" );
</script>
|
Output1 3 2 5 4
1 2
3 2 1
1 2 3
2 1 4 3 5
1 2 6 5 4 3
3 2 1 6 5 4 7 9 8
Time Complexity: O(N2) ,here N is length of string .
Auxiliary Space: O(N) since N extra space has been taken.
This solution is suggested by Ashutosh Kumar.
Method 3
We can that when we encounter I, we got numbers in increasing order but if we encounter ‘D’, we want to have numbers in decreasing order. Length of the output string is always one more than the input string. So the loop is from 0 to the length of the string. We have to take numbers from 1-9 so we always push (i+1) to our stack. Then we check what is the resulting character at the specified index.So, there will be two cases which are as follows:-
Case 1: If we have encountered I or we are at the last character of input string, then pop from the stack and add it to the end of the output string until the stack gets empty.
Case 2: If we have encountered D, then we want the numbers in decreasing order. so we just push (i+1) to our stack.
C++
#include <bits/stdc++.h>
using namespace std;
void PrintMinNumberForPattern(string seq)
{
string result;
stack< int > stk;
for ( int i = 0; i <= seq.length(); i++)
{
stk.push(i + 1);
if (i == seq.length() || seq[i] == 'I' )
{
while (!stk.empty())
{
result += to_string(stk.top());
result += " " ;
stk.pop();
}
}
}
cout << result << endl;
}
int main()
{
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
return 0;
}
|
Java
import java.util.Stack;
class GFG {
static void PrintMinNumberForPattern(String seq) {
String result = "" ;
Stack<Integer> stk = new Stack<Integer>();
for ( int i = 0 ; i <= seq.length(); i++) {
stk.push(i + 1 );
if (i == seq.length() || seq.charAt(i) == 'I' ) {
while (!stk.empty()) {
result += String.valueOf(stk.peek());
result += " " ;
stk.pop();
}
}
}
System.out.println(result);
}
public static void main(String[] args) {
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
}
}
|
Python3
def PrintMinNumberForPattern(Strr):
stack = []
res = ''
for i in range ( len (Strr) + 1 ):
stack.append(i + 1 )
if (i = = len (Strr) or Strr[i] = = 'I' ):
while len (stack) > 0 :
res + = str (stack.pop())
res + = ' '
print (res)
PrintMinNumberForPattern( "IDID" )
PrintMinNumberForPattern( "I" )
PrintMinNumberForPattern( "DD" )
PrintMinNumberForPattern( "II" )
PrintMinNumberForPattern( "DIDI" )
PrintMinNumberForPattern( "IIDDD" )
PrintMinNumberForPattern( "DDIDDIID" )
|
C#
using System;
using System.Collections;
public class GFG {
static void PrintMinNumberForPattern(String seq) {
String result = "" ;
Stack stk = new Stack();
for ( int i = 0; i <= seq.Length; i++) {
stk.Push(i + 1);
if (i == seq.Length || seq[i] == 'I' ) {
while (stk.Count!=0) {
result += String.Join( "" ,stk.Peek());
result += " " ;
stk.Pop();
}
}
}
Console.WriteLine(result);
}
public static void Main() {
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
}
}
|
Javascript
<script>
function PrintMinNumberForPattern(seq)
{
let result = "" ;
let stk = [];
for (let i = 0; i <= seq.length; i++)
{
stk.push(i + 1);
if (i == seq.length || seq[i] == 'I' )
{
while (stk.length!=0) {
result +=
(stk[stk.length - 1]).toString();
result += " " ;
stk.pop();
}
}
}
document.write(result + "</br>" );
}
PrintMinNumberForPattern( "IDID" );
PrintMinNumberForPattern( "I" );
PrintMinNumberForPattern( "DD" );
PrintMinNumberForPattern( "II" );
PrintMinNumberForPattern( "DIDI" );
PrintMinNumberForPattern( "IIDDD" );
PrintMinNumberForPattern( "DDIDDIID" );
</script>
|
Output1 3 2 5 4
1 2
3 2 1
1 2 3
2 1 4 3 5
1 2 6 5 4 3
3 2 1 6 5 4 7 9 8
Time Complexity: O(n)
Auxiliary Space: O(n), since n extra space has been taken.
This method is contributed by Roshni Agarwal.
Method 4 (Using two pointers)
Observation
- Since we have to find a minimum number without repeating digits, maximum length of output can be 9 (using each 1-9 digits once)
- Length of the output will be exactly one greater than input length.
- The idea is to iterate over the string and do the following if current character is ‘I’ or string is ended.
- Assign count in increasing order to each element from current-1 to the next left index of ‘I’ (or starting index is reached).
- Increase the count by 1.
Input : IDID
Output : 13254
Input : I
Output : 12
Input : DD
Output : 321
Input : II
Output : 123
Input : DIDI
Output : 21435
Input : IIDDD
Output : 126543
Input : DDIDDIID
Output : 321654798
Below is the implementation of above approach:
C++
#include <bits/stdc++.h>
using namespace std;
string getMinNumberForPattern(string seq)
{
int n = seq.length();
if (n >= 9)
return "-1" ;
string result(n+1, ' ' );
int count = 1;
for ( int i = 0; i <= n; i++)
{
if (i == n || seq[i] == 'I' )
{
for ( int j = i - 1 ; j >= -1 ; j--)
{
result[j + 1] = '0' + count++;
if (j >= 0 && seq[j] == 'I' )
break ;
}
}
}
return result;
}
int main()
{
string inputs[] = { "IDID" , "I" , "DD" , "II" , "DIDI" , "IIDDD" , "DDIDDIID" };
for (string input : inputs)
{
cout << getMinNumberForPattern(input) << "\n" ;
}
return 0;
}
|
Java
import java.io.IOException;
public class Test
{
static String getMinNumberForPattern(String seq)
{
int n = seq.length();
if (n >= 9 )
return "-1" ;
char result[] = new char [n + 1 ];
int count = 1 ;
for ( int i = 0 ; i <= n; i++)
{
if (i == n || seq.charAt(i) == 'I' )
{
for ( int j = i - 1 ; j >= - 1 ; j--)
{
result[j + 1 ] = ( char ) (( int ) '0' + count++);
if (j >= 0 && seq.charAt(j) == 'I' )
break ;
}
}
}
return new String(result);
}
public static void main(String[] args) throws IOException
{
String inputs[] = { "IDID" , "I" , "DD" , "II" , "DIDI" , "IIDDD" , "DDIDDIID" };
for (String input : inputs)
{
System.out.println(getMinNumberForPattern(input));
}
}
}
|
Python3
def getMinNumberForPattern(seq):
n = len (seq)
if (n > = 9 ):
return "-1"
result = [ None ] * (n + 1 )
count = 1
for i in range (n + 1 ):
if (i = = n or seq[i] = = 'I' ):
for j in range (i - 1 , - 2 , - 1 ):
result[j + 1 ] = int ( '0' + str (count))
count + = 1
if (j > = 0 and seq[j] = = 'I' ):
break
return result
if __name__ = = '__main__' :
inputs = [ "IDID" , "I" , "DD" , "II" ,
"DIDI" , "IIDDD" , "DDIDDIID" ]
for Input in inputs:
print ( * (getMinNumberForPattern( Input )))
|
C#
using System;
class GFG
{
static String getMinNumberForPattern(String seq)
{
int n = seq.Length;
if (n >= 9)
return "-1" ;
char []result = new char [n + 1];
int count = 1;
for ( int i = 0; i <= n; i++)
{
if (i == n || seq[i] == 'I' )
{
for ( int j = i - 1; j >= -1; j--)
{
result[j + 1] = ( char ) (( int ) '0' + count++);
if (j >= 0 && seq[j] == 'I' )
break ;
}
}
}
return new String(result);
}
public static void Main()
{
String []inputs = { "IDID" , "I" , "DD" , "II" ,
"DIDI" , "IIDDD" , "DDIDDIID" };
foreach (String input in inputs)
{
Console.WriteLine(getMinNumberForPattern(input));
}
}
}
|
Javascript
<script>
function getMinNumberForPattern(seq)
{
let n = seq.length;
if (n >= 9)
return "-1" ;
let result = new Array(n + 1);
let count = 1;
for (let i = 0; i <= n; i++)
{
if (i == n || seq[i] == 'I' )
{
for (let j = i - 1; j >= -1; j--)
{
result[j + 1] =
String.fromCharCode( '0' .charCodeAt() +
count++);
if (j >= 0 && seq[j] == 'I' )
break ;
}
}
}
return result.join( "" );
}
let inputs = [ "IDID" , "I" , "DD" , "II" , "DIDI" ,
"IIDDD" , "DDIDDIID" ];
for (let input = 0; input < inputs.length; input++)
{
document.write(
getMinNumberForPattern(inputs[input]) + "</br>"
);
}
</script>
|
Output13254
12
321
123
21435
126543
321654798
Time Complexity: O(N)
Auxiliary Space: O(N), since N extra space has been taken.
This solution is suggested by Brij Desai.
Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above
Method 5 (Start with the Smallest)
Start with the smallest number as the answer and keep shifting the digits when we encounter a D.
There is no need to traverse back for the index.
Follow the below steps,
- Start with the smallest number for len(s)+1 (say for DI, start with “123”)
- Now, starting with the second digit (index 1) and first character (D), iterate until end of the digits list, keeping track of the first D in a sequence of Ds
- When we encounter a D
move the digit at current index to the first D in the sequence - When we encounter an I
reset the last known location of D. Nothing to move as the digit is correctly placed (as of now…)
Below is the implementation of the above approach:
C++
#include <iostream>
#include <stdlib.h>
#include <string>
#include <vector>
using namespace std;
vector<string> didi_seq_gen(string s)
{
if (s.size() == 0)
return {};
vector<string> base_list = { "1" };
for ( int i = 2; i < s.size() + 2; i++)
base_list.push_back(to_string(i));
int last_D = -1;
for ( int i = 1; i < base_list.size(); i++) {
if (s[i - 1] == 'D' ) {
if (last_D < 0)
last_D = i - 1;
string v = base_list[i];
base_list.erase(base_list.begin() + i);
base_list.insert(base_list.begin() + last_D, v);
}
else
last_D = -1;
}
return base_list;
}
int main()
{
vector<string> inputs
= { "IDID" , "I" , "DD" , "II" ,
"DIDI" , "IIDDD" , "DDIDDIID" };
for ( auto x : inputs) {
vector<string> ans = didi_seq_gen(x);
for ( auto i : ans) {
cout << i;
}
cout << endl;
}
return 0;
}
|
Java
import java.util.*;
public class Main {
public static void main(String[] args)
{
String[] inputs
= { "IDID" , "I" , "DD" , "II" ,
"DIDI" , "IIDDD" , "DDIDDIID" };
for (String x : inputs) {
List<String> ans = didi_seq_gen(x);
for (String i : ans) {
System.out.print(i);
}
System.out.println();
}
}
public static List<String> didi_seq_gen(String s)
{
if (s.length() == 0 )
return new ArrayList<>();
List<String> base_list
= new ArrayList<>(Arrays.asList( "1" ));
for ( int i = 2 ; i < s.length() + 2 ; i++)
base_list.add(Integer.toString(i));
int last_D = - 1 ;
for ( int i = 1 ; i < base_list.size(); i++) {
if (s.charAt(i - 1 ) == 'D' ) {
if (last_D < 0 )
last_D = i - 1 ;
String v = base_list.get(i);
base_list.remove(i);
base_list.add(last_D, v);
}
else {
last_D = - 1 ;
}
}
return base_list;
}
}
|
Python3
def didi_seq_gen(s: str ):
if not s or len (s) < = 0 :
return ""
base_list = [ "1" ]
for i in range ( 1 , len (s) + 1 ):
base_list.append(f '{i + 1}' )
last_D = - 1
for i in range ( 1 , len (base_list)):
if s[i - 1 ] = = 'D' :
if last_D < 0 :
last_D = i - 1
v = base_list[i]
del base_list[i]
base_list.insert(last_D, v)
else :
last_D = - 1
return base_list
print (didi_seq_gen( "IDID" ))
print (didi_seq_gen( "I" ))
print (didi_seq_gen( "DD" ))
print (didi_seq_gen( "II" ))
print (didi_seq_gen( "DIDI" ))
print (didi_seq_gen( "IIDDD" ))
print (didi_seq_gen( "DDIDDIID" ))
|
C#
using System;
using System.Collections.Generic;
using System.Linq;
using System.Collections;
public class GFG
{
public static void Main(String[] args)
{
String[] inputs = { "IDID" , "I" , "DD" , "II" , "DIDI" , "IIDDD" , "DDIDDIID" };
foreach (String x in inputs)
{
var ans = GFG.didi_seq_gen(x);
foreach (String i in ans)
{
Console.Write(i);
}
Console.WriteLine();
}
}
public static List<String> didi_seq_gen(String s)
{
if (s.Length == 0)
{
return new List<String>();
}
var base_list = new List<String>();
base_list.Add( "1" );
for ( int i = 2; i < s.Length + 2; i++)
{
base_list.Add(Convert.ToString(i));
}
var last_D = -1;
for ( int i = 1; i < base_list.Count; i++)
{
if (s[i - 1] == 'D' )
{
if (last_D < 0)
{
last_D = i - 1;
}
var v = base_list[i];
base_list.RemoveAt(i);
base_list.Insert(last_D,v);
}
else
{
last_D = -1;
}
}
return base_list;
}
}
|
Javascript
function didi_seq_gen(s)
{
if (!s || s.length <= 0)
return ""
let base_list = [ "1" ]
for ( var i = 1; i <= s.length; i++)
base_list.push((i + 1).toString())
let last_D = -1
for ( var i = 1; i < base_list.length; i++)
{
if (s[i - 1] == 'D' )
{
if (last_D < 0)
last_D = i - 1
v = base_list[i]
base_list.splice(i, 1)
base_list.splice(last_D, 0, v)
}
else
last_D = -1
}
return base_list.join( "" )
}
console.log(didi_seq_gen( "IDID" ))
console.log(didi_seq_gen( "I" ))
console.log(didi_seq_gen( "DD" ))
console.log(didi_seq_gen( "II" ))
console.log(didi_seq_gen( "DIDI" ))
console.log(didi_seq_gen( "IIDDD" ))
console.log(didi_seq_gen( "DDIDDIID" ))
|
Output13254
12
321
123
21435
126543
321654798
Time Complexity: O(N)
Auxiliary Space: O(N)
Method 6 : (Space Optimized and modular code of Method 1)
Examples:
Input: "DDDD"
Output: "432156"
For input 1, pattern is like, D -> D -> D -> D
5 4 3 2 1
Input: "DDDII"
Output: "432156"
For input 2, pattern is like, D -> D -> D -> I -> I
4 3 2 1 5 6
Input: "IIDIDIII"
Output: "124365789"
For input 3, pattern is like, I -> I -> D -> I -> D -> I -> I -> I
1 2 4 3 6 5 7 8 9
Approach:
- Think if the string contains only characters ‘I’ increasing, then there isn’t any problem you can just print and keep incrementing.
- Now think if the string contains only characters ‘D’ increasing, then you somehow have to get the number ‘D’ characters present from initial point, so that you can start from total count of ‘D’ and print by decrementing.
- The problem is when you encounter character ‘D’ after character ‘I’. Here somehow you have to get count of ‘D’ to get the next possible decremental start for ‘D’ and then print by decrementing until you have encountered all of ‘D’.
- Here in this approach the code has been made more modular compared to method 1 of space optimized version.
C++
#include <bits/stdc++.h>
using namespace std;
string findMinNumberPattern(string str)
{
string ans = "" ;
int i = 0;
int cur = 1;
int dCount = 0;
while (i < str.length()) {
char ch = str[i];
if (i == 0 && ch == 'I' ) {
ans += to_string(cur);
cur++;
}
if (ch == 'D' ) {
dCount++;
}
int j = i + 1;
while (j < str.length()
&& str[j] == 'D' ) {
dCount++;
j++;
}
int k = dCount;
while (dCount >= 0) {
ans += to_string(cur + dCount);
dCount--;
}
cur += (k + 1);
dCount = 0;
i = j;
}
return ans;
}
int main()
{
cout << (findMinNumberPattern( "DIDID" )) << endl;
cout << (findMinNumberPattern( "DIDIII" )) << endl;
cout << (findMinNumberPattern( "DDDIIDI" )) << endl;
cout << (findMinNumberPattern( "IDIDIID" )) << endl;
cout << (findMinNumberPattern( "DIIDIDD" )) << endl;
cout << (findMinNumberPattern( "IIDIDDD" )) << endl;
return 0;
}
|
Java
import java.io.*;
class GFG {
public static String findMinNumberPattern(String str)
{
String ans = "" ;
int i = 0 ;
int cur = 1 ;
int dCount = 0 ;
while (i < str.length()) {
char ch = str.charAt(i);
if (i == 0 && ch == 'I' ) {
ans += cur;
cur++;
}
if (ch == 'D' ) {
dCount++;
}
int j = i + 1 ;
while (j < str.length()
&& str.charAt(j) == 'D' ) {
dCount++;
j++;
}
int k = dCount;
while (dCount >= 0 ) {
ans += (cur + dCount);
dCount--;
}
cur += (k + 1 );
dCount = 0 ;
i = j;
}
return ans;
}
public static void main(String[] args)
{
System.out.println(findMinNumberPattern( "DIDID" ));
System.out.println(findMinNumberPattern( "DIDIII" ));
System.out.println(findMinNumberPattern( "DDDIIDI" ));
System.out.println(findMinNumberPattern( "IDIDIID" ));
System.out.println(findMinNumberPattern( "DIIDIDD" ));
System.out.println(findMinNumberPattern( "IIDIDDD" ));
}
}
|
Python3
def findMinNumberPattern( Str ):
ans = ""
i = 0
cur = 1
dCount = 0
while (i < len ( Str )) :
ch = Str [i]
if (i = = 0 and ch = = 'I' ) :
ans + = str (cur)
cur + = 1
if (ch = = 'D' ) :
dCount + = 1
j = i + 1
while (j < len ( Str ) and Str [j] = = 'D' ) :
dCount + = 1
j + = 1
k = dCount
while (dCount > = 0 ) :
ans + = str (cur + dCount)
dCount - = 1
cur + = (k + 1 )
dCount = 0
i = j
return ans
print (findMinNumberPattern( "DIDID" ))
print (findMinNumberPattern( "DIDIII" ))
print (findMinNumberPattern( "DDDIIDI" ))
print (findMinNumberPattern( "IDIDIID" ))
print (findMinNumberPattern( "DIIDIDD" ))
print (findMinNumberPattern( "IIDIDDD" ))
|
C#
using System;
class GFG {
public static string findMinNumberPattern( string str)
{
string ans = "" ;
int i = 0;
int cur = 1;
int dCount = 0;
while (i < str.Length) {
char ch = str[i];
if (i == 0 && ch == 'I' ) {
ans += cur;
cur++;
}
if (ch == 'D' ) {
dCount++;
}
int j = i + 1;
while (j < str.Length
&& str[j] == 'D' ) {
dCount++;
j++;
}
int k = dCount;
while (dCount >= 0) {
ans += (cur + dCount);
dCount--;
}
cur += (k + 1);
dCount = 0;
i = j;
}
return ans;
}
static void Main() {
Console.WriteLine(findMinNumberPattern( "DIDID" ));
Console.WriteLine(findMinNumberPattern( "DIDIII" ));
Console.WriteLine(findMinNumberPattern( "DDDIIDI" ));
Console.WriteLine(findMinNumberPattern( "IDIDIID" ));
Console.WriteLine(findMinNumberPattern( "DIIDIDD" ));
Console.WriteLine(findMinNumberPattern( "IIDIDDD" ));
}
}
|
Javascript
<script>
function findMinNumberPattern(str)
{
let ans = "" ;
let i = 0;
let cur = 1;
let dCount = 0;
while (i < str.length) {
let ch = str[i];
if (i == 0 && ch == 'I' ) {
ans += cur;
cur++;
}
if (ch == 'D' ) {
dCount++;
}
let j = i + 1;
while (j < str.length
&& str[j] == 'D' ) {
dCount++;
j++;
}
let k = dCount;
while (dCount >= 0) {
ans += (cur + dCount);
dCount--;
}
cur += (k + 1);
dCount = 0;
i = j;
}
return ans;
}
document.write(findMinNumberPattern( "DIDID" )+ "<br>" );
document.write(findMinNumberPattern( "DIDIII" )+ "<br>" );
document.write(findMinNumberPattern( "DDDIIDI" )+ "<br>" );
document.write(findMinNumberPattern( "IDIDIID" )+ "<br>" );
document.write(findMinNumberPattern( "DIIDIDD" )+ "<br>" );
document.write(findMinNumberPattern( "IIDIDDD" )+ "<br>" );
</script>
|
Output214365
2143567
43215768
13254687
21354876
12438765
Time Complexity : O(n)
Auxiliary Space : O(1)
Method 7: (Substring Reversals)
The idea is to take the smallest number with len(s)+1 and perform reversals for every substring containing only ‘D’.
Follow below steps to solve the problem:
1. Create the smallest possible number of length len(s)+1.
2. Traverse the string (say i).
3. Find the first and last occurrence of ‘D’ for every substring containing only ‘D’.
4. Reverse every such substring and reinitialize first and last occurrence.
C++14
#include <bits/stdc++.h>
using namespace std;
string get_num_seq(string& str_seq)
{
int n=str_seq.length(),start=-1,end=-1;
string ans;
for ( int i=1;i<=n+1;i++)
ans.push_back(i+48);
for ( int i=0;i<n;i++)
{
if (str_seq[i]== 'D' )
{
if (start==-1)
start=i;
end=i;
}
else {
if (start!=-1)
reverse(ans.begin()+start,ans.begin()+end+2);
start=-1;
end=-1;
}
}
if (start!=-1)
reverse(ans.begin()+start,ans.begin()+end+2);
return ans;
}
int main()
{
string str_seq= "DDIDDIID" ;
cout<<get_num_seq(str_seq);
return 0;
}
|
Java
import java.io.*;
class GFG {
public static String getNumSeq(String strSeq)
{
int n = strSeq.length();
int start = - 1 ;
int end = - 1 ;
String ans = "" ;
for ( int i = 1 ; i <= n + 1 ; i++) {
ans += String.valueOf(i);
}
for ( int i = 0 ; i < n; i++) {
if (strSeq.charAt(i) == 'D' ) {
if (start == - 1 ) {
start = i;
}
end = i;
}
else {
if (start != - 1 ) {
ans = reverse(ans, start, end + 2 );
}
start = - 1 ;
end = - 1 ;
}
}
if (start != - 1 ) {
ans = reverse(ans, start, end + 2 );
}
return ans;
}
public static String reverse(String str, int start,
int end)
{
char [] arr = str.toCharArray();
for ( int i = start, j = end - 1 ; i < j; i++, j--) {
char temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
return new String(arr);
}
public static void main(String[] args)
{
String strSeq = "DDIDDIID" ;
System.out.println(getNumSeq(strSeq));
}
}
|
Python3
def get_num_seq( str_seq):
n = len (str_seq)
start = - 1
end = - 1 ;
ans = "";
for i in range ( 1 , n + 2 ):
ans + = str (i)
for i in range (n):
if (str_seq[i] = = 'D' ):
if (start = = - 1 ):
start = i;
end = i;
else :
if (start ! = - 1 ):
ans = ans[:start] + ans[start:end + 2 ][:: - 1 ] + ans[end + 2 :]
start = - 1 ;
end = - 1 ;
if (start ! = - 1 ):
ans = ans[:start] + ans[start:end + 2 ][:: - 1 ] + ans[end + 2 :]
return ans;
str_seq = "DDIDDIID" ;
print (get_num_seq(str_seq))
|
C#
using System;
public class GFG {
public static string GetNumSeq( string strSeq)
{
int n = strSeq.Length;
int start = -1;
int end = -1;
string ans = "" ;
for ( int i = 1; i <= n + 1; i++) {
ans += i.ToString();
}
for ( int i = 0; i < n; i++) {
if (strSeq[i] == 'D' ) {
if (start == -1) {
start = i;
}
end = i;
}
else {
if (start != -1) {
ans = Reverse(ans, start, end + 2);
}
start = -1;
end = -1;
}
}
if (start != -1) {
ans = Reverse(ans, start, end + 2);
}
return ans;
}
public static string Reverse( string str, int start,
int end)
{
char [] arr = str.ToCharArray();
for ( int i = start, j = end - 1; i < j; i++, j--) {
char temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
return new string (arr);
}
static public void Main()
{
string strSeq = "DDIDDIID" ;
Console.WriteLine(GetNumSeq(strSeq));
}
}
|
Javascript
function get_num_seq(strSeq) {
let n = strSeq.length;
let start = -1;
let end = -1;
let ans = "" ;
for (let i = 1; i <= n + 1; i++) {
ans += String.fromCharCode(i+48);
}
for (let i = 0; i < n; i++) {
if (strSeq[i] === 'D' ) {
if (start === -1) {
start = i;
}
end = i;
} else {
if (start !== -1) {
ans = ans.slice(0, start) + ans.slice(start, end + 2).split( "" ).reverse().join( "" ) + ans.slice(end + 2);
}
start = -1;
end = -1;
}
}
if (start !== -1) {
ans = ans.slice(0, start) + ans.slice(start, end + 2).split( "" ).reverse().join( "" ) + ans.slice(end + 2);
}
return ans;
}
let str_seq= "DDIDDIID" ;
document.write(get_num_seq(str_seq));
|
Time Complexity: O(n)
Auxiliary Space: O(1)