Article Categories
- All Categories
-
Data Structure
-
Networking
-
RDBMS
-
Operating System
-
Java
-
MS Excel
-
iOS
-
HTML
-
CSS
-
Android
-
Python
-
C Programming
-
C++
-
C#
-
MongoDB
-
MySQL
-
Javascript
-
PHP
-
Economics & Finance
C/C++ Program to Count number of binary strings without consecutive 1’s?
In this article, we will learn how to count all distinct binary strings of length n such that no two 1's appear consecutively. We'll explore this problem using both recursive and dynamic programming approaches in C.
What is a Binary String?
A binary string is a sequence of characters that contains only '0' and '1'. It represents information in base-2 format. For example, "0101" is a binary string of length 4.
We are given a positive integer n, and our task is to count all possible distinct binary strings of length n that do not contain consecutive 1's.
Consider the following example scenarios to understand the problem better −
Scenario 1
Input: n = 3
Output: 5
Explanation:
Valid strings: {"000", "001", "010", "100", "101"}
Scenario 2
Input: n = 4
Output: 8
Explanation:
Valid strings: {"0000", "0001", "0010", "0100", "0101", "1000", "1001", "1010"}
Approaches
To solve this problem, there are the following approaches −
- Using Recursion
- Using Bottom-Up Dynamic Programming (Tabulation)
Let us learn each approach in detail with the help of examples.
Method 1: Using Recursive Solution
In this approach, we use recursion to build binary strings step-by-step while making sure that no two consecutive 1's appear. The key insight is that at each position, we can either place '0' or '1', but if the last placed bit is '1', we must place '0' next to avoid consecutive 1's.
Example
#include <stdio.h>
int count_strings(int n, int last_digit) {
if (n == 0) return 1;
if (n == 1) return last_digit ? 1 : 2;
if (last_digit == 0) {
/* If last digit is 0, we can place both 0 and 1 */
return count_strings(n - 1, 0) + count_strings(n - 1, 1);
} else {
/* If last digit is 1, we can only place 0 */
return count_strings(n - 1, 0);
}
}
int main() {
int n = 4;
printf("Number of %d-digit binary strings without consecutive 1's: %d\n",
n, count_strings(n, 0));
return 0;
}
Number of 4-digit binary strings without consecutive 1's: 8
Time and Space Complexity
- Time Complexity: O(2n) due to exponential recursion
- Space Complexity: O(n) due to recursion stack depth
Method 2: Using Bottom-Up Dynamic Programming
We can optimize the recursive approach using dynamic programming. We use a DP array where dp[i] stores the count of valid binary strings of length i. The recurrence relation follows the Fibonacci pattern −
dp[i] = dp[i-1] + dp[i-2]
Example
#include <stdio.h>
int count_strings(int n) {
if (n == 1) return 2;
if (n == 2) return 3;
int dp[n + 1];
dp[1] = 2; /* Strings: "0", "1" */
dp[2] = 3; /* Strings: "00", "01", "10" */
for (int i = 3; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2];
}
return dp[n];
}
int main() {
int n = 5;
printf("Number of %d-digit binary strings without consecutive 1's: %d\n",
n, count_strings(n));
return 0;
}
Number of 5-digit binary strings without consecutive 1's: 13
Time and Space Complexity
- Time Complexity: O(n) - single loop iteration
- Space Complexity: O(n) - for DP array storage
Space-Optimized DP Solution
We can further optimize space complexity by using only two variables instead of an array −
#include <stdio.h>
int count_strings_optimized(int n) {
if (n == 1) return 2;
if (n == 2) return 3;
int prev2 = 2; /* dp[1] */
int prev1 = 3; /* dp[2] */
int current;
for (int i = 3; i <= n; i++) {
current = prev1 + prev2;
prev2 = prev1;
prev1 = current;
}
return current;
}
int main() {
int n = 6;
printf("Number of %d-digit binary strings without consecutive 1's: %d\n",
n, count_strings_optimized(n));
return 0;
}
Number of 6-digit binary strings without consecutive 1's: 21
Key Points
- The problem follows Fibonacci sequence pattern: f(n) = f(n-1) + f(n-2)
- Base cases: f(1) = 2, f(2) = 3
- Dynamic programming provides optimal O(n) time solution
- Space can be optimized to O(1) using two variables
Conclusion
Counting binary strings without consecutive 1's can be solved efficiently using dynamic programming with O(n) time complexity. The problem follows the Fibonacci pattern, making it a classic example of optimizing recursive solutions.
