Print Longest substring without repeating characters
Last Updated :
23 Apr, 2025
Given a string s having lowercase characters, find the length of the longest substring without repeating characters.
Examples:
Input: s = “geeksforgeeks”
Output: 7
Explanation: The longest substrings without repeating characters are “eksforg” and “ksforge”, with lengths of 7.
Input: s = “aaa”
Output: 1
Explanation: The longest substring without repeating characters is “a”
Input: s = “abcdefabcbb”
Output: 6
Explanation: The longest substring without repeating characters is “abcdef”.
Given a string, print the longest substring without repeating characters. For example, the longest substrings without repeating characters for “ABDEFGABEF” are “BDEFGA” and “DEFGAB”, with length 6. For “BBBB” the longest substring is “B”, with length 1. The desired time complexity is O(n) where n is the length of the string.
Examples:
Input : GEEKSFORGEEKS
Output : EKSFORG
Input : ABDEFGABEF
Output : BDEFGA
Approach:
The idea is to traverse the string and for each already visited character store its last occurrence in a hash table(Here unordered_map is used as a hash with key as character and value as its last position). The variable st stores the starting point of the current substring, maxlen stores the length of maximum length substring, and start stores the starting index of maximum length substring. While traversing the string, check whether the current character is present in the hash table or not.
If it is not present, then store the current character in the hash table with value as the current index. If it is already present in the hash table, this means the current character could repeat in the current substring. For this check, if the previous occurrence of character is before or after the starting point st of the current substring. If it is before st, then only update the value in the hash table. If it is after st, then find the length of current substring currlen as i-st, where i is the current index. Compare currlen with maxlen. If maxlen is less than currlen, then update maxlen as currlen and start as st. After complete traversal of the string, the required the longest substring without repeating characters is from s[start] to s[start+maxlen-1].
Implementation:
C++
// C++ program to find and print longest
// substring without repeating characters.
#include <bits/stdc++.h>
using namespace std;
// Function to find and print longest
// substring without repeating characters.
string findLongestSubstring(string str)
{
int i;
int n = str.length();
// starting point of current substring.
int st = 0;
// length of current substring.
int currlen;
// maximum length substring without repeating
// characters.
int maxlen = 0;
// starting index of maximum length substring.
int start;
// Hash Map to store last occurrence of each
// already visited character.
unordered_map<char, int> pos;
// Last occurrence of first character is index 0;
pos[str[0]] = 0;
for (i = 1; i < n; i++) {
// If this character is not present in hash,
// then this is first occurrence of this
// character, store this in hash.
if (pos.find(str[i]) == pos.end())
pos[str[i]] = i;
else {
// If this character is present in hash then
// this character has previous occurrence,
// check if that occurrence is before or after
// starting point of current substring.
if (pos[str[i]] >= st) {
// find length of current substring and
// update maxlen and start accordingly.
currlen = i - st;
if (maxlen < currlen) {
maxlen = currlen;
start = st;
}
// Next substring will start after the last
// occurrence of current character to avoid
// its repetition.
st = pos[str[i]] + 1;
}
// Update last occurrence of
// current character.
pos[str[i]] = i;
}
}
// Compare length of last substring with maxlen and
// update maxlen and start accordingly.
if (maxlen < i - st) {
maxlen = i - st;
start = st;
}
// The required longest substring without
// repeating characters is from str[start]
// to str[start+maxlen-1].
return str.substr(start, maxlen);
}
// Driver function
int main()
{
string str = "GEEKSFORGEEKS";
cout << findLongestSubstring(str);
return 0;
}
Java
// Java program to find
// and print longest substring
// without repeating characters.
import java.util.*;
class GFG{
// Function to find and print longest
// substring without repeating characters.
public static String findLongestSubstring(String str)
{
int i;
int n = str.length();
// Starting point
// of current substring.
int st = 0;
// length of
// current substring.
int currlen = 0;
// maximum length
// substring without
// repeating characters.
int maxlen = 0;
// starting index of
// maximum length substring.
int start = 0;
// Hash Map to store last
// occurrence of each
// already visited character.
HashMap<Character,
Integer> pos = new HashMap<Character,
Integer>();
// Last occurrence of first
// character is index 0;
pos.put(str.charAt(0), 0);
for (i = 1; i < n; i++)
{
// If this character is not present in hash,
// then this is first occurrence of this
// character, store this in hash.
if (!pos.containsKey(str.charAt(i)))
{
pos.put(str.charAt(i), i);
}
else
{
// If this character is present
// in hash then this character
// has previous occurrence,
// check if that occurrence
// is before or after starting
// point of current substring.
if (pos.get(str.charAt(i)) >= st)
{
// find length of current
// substring and update maxlen
// and start accordingly.
currlen = i - st;
if (maxlen < currlen)
{
maxlen = currlen;
start = st;
}
// Next substring will start
// after the last occurrence
// of current character to avoid
// its repetition.
st = pos.get(str.charAt(i)) + 1;
}
// Update last occurrence of
// current character.
pos.replace(str.charAt(i), i);
}
}
// Compare length of last
// substring with maxlen and
// update maxlen and start
// accordingly.
if (maxlen < i - st)
{
maxlen = i - st;
start = st;
}
// The required longest
// substring without
// repeating characters
// is from str[start]
// to str[start+maxlen-1].
return str.substring(start,
start +
maxlen);
}
// Driver Code
public static void main(String[] args)
{
String str = "GEEKSFORGEEKS";
System.out.print(findLongestSubstring(str));
}
}
// This code is contributed by divyeshrabadiya07
Python
# Python3 program to find and print longest
# substring without repeating characters.
# Function to find and print longest
# substring without repeating characters.
def findLongestSubstring(string):
n = len(string)
# starting point of current substring.
st = 0
# maximum length substring without
# repeating characters.
maxlen = 0
# starting index of maximum
# length substring.
start = 0
# Hash Map to store last occurrence
# of each already visited character.
pos = {}
# Last occurrence of first
# character is index 0
pos[string[0]] = 0
for i in range(1, n):
# If this character is not present in hash,
# then this is first occurrence of this
# character, store this in hash.
if string[i] not in pos:
pos[string[i]] = i
else:
# If this character is present in hash then
# this character has previous occurrence,
# check if that occurrence is before or after
# starting point of current substring.
if pos[string[i]] >= st:
# find length of current substring and
# update maxlen and start accordingly.
currlen = i - st
if maxlen < currlen:
maxlen = currlen
start = st
# Next substring will start after the last
# occurrence of current character to avoid
# its repetition.
st = pos[string[i]] + 1
# Update last occurrence of
# current character.
pos[string[i]] = i
# Compare length of last substring with maxlen
# and update maxlen and start accordingly.
if maxlen < i - st:
maxlen = i - st
start = st
# The required longest substring without
# repeating characters is from string[start]
# to string[start+maxlen-1].
return string[start : start + maxlen]
# Driver Code
if __name__ == "__main__":
string = "GEEKSFORGEEKS"
print(findLongestSubstring(string))
# This code is contributed by Rituraj Jain
C#
// C# program to find
// and print longest substring
// without repeating characters.
using System;
using System.Collections.Generic;
class GFG{
// Function to find and
// print longest substring
// without repeating characters.
public static String findlongestSubstring(String str)
{
int i;
int n = str.Length;
// Starting point
// of current substring.
int st = 0;
// length of
// current substring.
int currlen = 0;
// maximum length
// substring without
// repeating characters.
int maxlen = 0;
// starting index of
// maximum length substring.
int start = 0;
// Hash Map to store last
// occurrence of each
// already visited character.
Dictionary<char,
int> pos = new Dictionary<char,
int>();
// Last occurrence of first
// character is index 0;
pos.Add(str[0], 0);
for (i = 1; i < n; i++)
{
// If this character is not present in hash,
// then this is first occurrence of this
// character, store this in hash.
if (!pos.ContainsKey(str[i]))
{
pos.Add(str[i], i);
}
else
{
// If this character is present
// in hash then this character
// has previous occurrence,
// check if that occurrence
// is before or after starting
// point of current substring.
if (pos[str[i]] >= st)
{
// find length of current
// substring and update maxlen
// and start accordingly.
currlen = i - st;
if (maxlen < currlen)
{
maxlen = currlen;
start = st;
}
// Next substring will start
// after the last occurrence
// of current character to avoid
// its repetition.
st = pos[str[i]] + 1;
}
// Update last occurrence of
// current character.
pos[str[i]] = i;
}
}
// Compare length of last
// substring with maxlen and
// update maxlen and start
// accordingly.
if (maxlen < i - st)
{
maxlen = i - st;
start = st;
}
// The required longest
// substring without
// repeating characters
// is from str[start]
// to str[start+maxlen-1].
return str.Substring(start,
maxlen);
}
// Driver Code
public static void Main(String[] args)
{
String str = "GEEKSFORGEEKS";
Console.Write(findlongestSubstring(str));
}
}
// This code is contributed by shikhasingrajput
JavaScript
<script>
// JavaScript program for the above approach
// Function to find and print longest
// substring without repeating characters.
function findLongestSubstring(str)
{
var i;
var n = str.length;
// starting point of current substring.
var st = 0;
// length of current substring.
var currlen;
// maximum length substring without repeating
// characters.
var maxlen = 0;
// starting index of maximum length substring.
var start;
// Hash Map to store last occurrence of each
// already visited character.
var pos = new Map();
// Last occurrence of first character is index 0;
pos.set(str[0], 0);
for (var i = 1; i < n; i++) {
// If this character is not present in hash,
// then this is first occurrence of this
// character, store this in hash.
if (!pos.has(str[i]))
pos.set(str[i],i) ;
else {
// If this character is present in hash then
// this character has previous occurrence,
// check if that occurrence is before or after
// starting point of current substring.
if (pos.get(str[i]) >= st) {
// find length of current substring and
// update maxlen and start accordingly.
currlen = i - st;
if (maxlen < currlen) {
maxlen = currlen;
start = st;
}
// Next substring will start after the last
// occurrence of current character to avoid
// its repetition.
st = pos.get(str[i]) + 1;
}
// Update last occurrence of
// current character.
pos.set(str[i], i);
}
}
// Compare length of last substring with maxlen and
// update maxlen and start accordingly.
if (maxlen < i - st) {
maxlen = i - st;
start = st;
}
// The required longest substring without
// repeating characters is from str[start]
// to str[start+maxlen-1].
return str.substr(start,maxlen);
}
var str = "GEEKSFORGEEKS";
document.write(findLongestSubstring(str));
// This code is contributed by SoumikMondal
</script>
Complexity Analysis:
- Time Complexity: O(n)
- Auxiliary Space: O(n)
Another Approach:
- Initialize a hash set to keep track of the characters that have been visited and two variables l and r to mark the left and right ends of the current substring. Also, initialize variables maxL, maxR, and maxStr to keep track of the longest substring found so far.
- Iterate through the string using a while loop until the right pointer r reaches the end of the string.
- Check if the character s[r] is present in the hash set. If it's not present, insert it into the hash set and move the right pointer r to the next character.
- If the character s[r] is already present in the hash set, it means that the current substring has repeating characters. In this case, remove the character s[l] from the hash set and move the left pointer l to the next character. Repeat this step until the character s[r] is no longer present in the hash set.
- Check if the length of the current substring (r - l + 1) is greater than the length of the longest substring found so far (maxStr). If it is, update maxStr to the length of the current substring, and update maxL and maxR to the left and right pointers l and r.
- Once the loop is finished, use the maxL and maxR indices to print the longest substring without repeating characters.
Below is the implementation of above approach:
C++
#include <iostream>
#include <unordered_set>
using namespace std;
void printLongestSubstring(string s) {
int n = s.size();
int l = 0, r = 0;
unordered_set<char> visited;
int maxStr = 0;
int maxL = 0, maxR = 0;
while (r < n) {
if (visited.find(s[r]) == visited.end()) {
visited.insert(s[r]);
if (r - l + 1 > maxStr) {
maxStr = r - l + 1;
maxL = l;
maxR = r;
}
r++;
}
else {
visited.erase(s[l]);
l++;
}
}
for (int i = maxL; i <= maxR; i++) {
cout << s[i];
}
cout << endl;
}
int main() {
string str = "GEEKSFORGEEKS";
printLongestSubstring(str);
return 0;
}
Java
import java.util.HashSet;
public class Main {
public static void printLongestSubstring(String s)
{
int n = s.length();
int l = 0, r = 0;
HashSet<Character> visited = new HashSet<>();
int maxStr = 0;
int maxL = 0, maxR = 0;
while (r < n) {
if (!visited.contains(s.charAt(r))) {
visited.add(s.charAt(r));
if (r - l + 1 > maxStr) {
maxStr = r - l + 1;
maxL = l;
maxR = r;
}
r++;
}
else {
visited.remove(s.charAt(l));
l++;
}
}
for (int i = maxL; i <= maxR; i++) {
System.out.print(s.charAt(i));
}
System.out.println();
}
public static void main(String[] args)
{
String str = "GEEKSFORGEEKS";
printLongestSubstring(str);
}
}
// This code is contributed by Prajwal Kandekar
Python
def printLongestSubstring(s: str) -> None:
n = len(s)
l, r = 0, 0
visited = set()
maxStr = 0
maxL, maxR = 0, 0
while r < n:
if s[r] not in visited:
visited.add(s[r])
if r - l + 1 > maxStr:
maxStr = r - l + 1
maxL, maxR = l, r
r += 1
else:
visited.remove(s[l])
l += 1
print(s[maxL:maxR+1])
str = "GEEKSFORGEEKS"
printLongestSubstring(str)
C#
using System;
using System.Collections.Generic;
namespace LongestSubstring
{
class Program
{
static void printLongestSubstring(string s)
{
int n = s.Length;
int l = 0, r = 0;
HashSet<char> visited = new HashSet<char>();
int maxStr = 0;
int maxL = 0, maxR = 0;
while (r < n)
{
if (!visited.Contains(s[r]))
{
visited.Add(s[r]);
if (r - l + 1 > maxStr)
{
maxStr = r - l + 1;
maxL = l;
maxR = r;
}
r++;
}
else
{
visited.Remove(s[l]);
l++;
}
}
for (int i = maxL; i <= maxR; i++)
{
Console.Write(s[i]);
}
Console.WriteLine();
}
static void Main(string[] args)
{
string str = "GEEKSFORGEEKS";
printLongestSubstring(str);
Console.ReadKey();
}
}
}
JavaScript
function printLongestSubstring(s) {
const n = s.length;
let l = 0;
let r = 0;
const visited = new Set();
let maxStr = 0;
let maxL = 0;
let maxR = 0;
while (r < n) {
// Check if the character at s[r] has not been visited
if (!visited.has(s[r])) {
visited.add(s[r]);
// Calculate the length of the current substring
if (r - l + 1 > maxStr) {
maxStr = r - l + 1;
maxL = l;
maxR = r;
}
r++;
} else {
// If the character at s[r] has been visited, remove s[l] from the set
visited.delete(s[l]);
l++;
}
}
// Print the longest substring without repeating characters
let longestSubstring = '';
for (let i = maxL; i <= maxR; i++) {
longestSubstring += s[i];
}
console.log(longestSubstring);
}
// Main function
const str = "GEEKSFORGEEKS";
printLongestSubstring(str);
Time Complexity: O(n)
Auxiliary Space: O(1)
Similar Reads
DSA Tutorial - Learn Data Structures and Algorithms DSA (Data Structures and Algorithms) is the study of organizing data efficiently using data structures like arrays, stacks, and trees, paired with step-by-step procedures (or algorithms) to solve problems effectively. Data structures manage how data is stored and accessed, while algorithms focus on
7 min read
Quick Sort QuickSort is a sorting algorithm based on the Divide and Conquer that picks an element as a pivot and partitions the given array around the picked pivot by placing the pivot in its correct position in the sorted array. It works on the principle of divide and conquer, breaking down the problem into s
12 min read
Merge Sort - Data Structure and Algorithms Tutorials Merge sort is a popular sorting algorithm known for its efficiency and stability. It follows the divide-and-conquer approach. It works by recursively dividing the input array into two halves, recursively sorting the two halves and finally merging them back together to obtain the sorted array. Merge
14 min read
Data Structures Tutorial Data structures are the fundamental building blocks of computer programming. They define how data is organized, stored, and manipulated within a program. Understanding data structures is very important for developing efficient and effective algorithms. What is Data Structure?A data structure is a st
2 min read
Bubble Sort Algorithm Bubble Sort is the simplest sorting algorithm that works by repeatedly swapping the adjacent elements if they are in the wrong order. This algorithm is not suitable for large data sets as its average and worst-case time complexity are quite high.We sort the array using multiple passes. After the fir
8 min read
Breadth First Search or BFS for a Graph Given a undirected graph represented by an adjacency list adj, where each adj[i] represents the list of vertices connected to vertex i. Perform a Breadth First Search (BFS) traversal starting from vertex 0, visiting vertices from left to right according to the adjacency list, and return a list conta
15+ min read
Binary Search Algorithm - Iterative and Recursive Implementation Binary Search Algorithm is a searching algorithm used in a sorted array by repeatedly dividing the search interval in half. The idea of binary search is to use the information that the array is sorted and reduce the time complexity to O(log N). Binary Search AlgorithmConditions to apply Binary Searc
15 min read
Insertion Sort Algorithm Insertion sort is a simple sorting algorithm that works by iteratively inserting each element of an unsorted list into its correct position in a sorted portion of the list. It is like sorting playing cards in your hands. You split the cards into two groups: the sorted cards and the unsorted cards. T
9 min read
Array Data Structure Guide In this article, we introduce array, implementation in different popular languages, its basic operations and commonly seen problems / interview questions. An array stores items (in case of C/C++ and Java Primitive Arrays) or their references (in case of Python, JS, Java Non-Primitive) at contiguous
4 min read
Sorting Algorithms A Sorting Algorithm is used to rearrange a given array or list of elements in an order. For example, a given array [10, 20, 5, 2] becomes [2, 5, 10, 20] after sorting in increasing order and becomes [20, 10, 5, 2] after sorting in decreasing order. There exist different sorting algorithms for differ
3 min read