import
java.util.Arrays;
public
class
GFG {
static
boolean
isValid(String str, String pattern,
int
mid,
int
[] start) {
int
[] count =
new
int
[
256
];
int
distinct =
0
;
boolean
found =
false
;
for
(
char
c : pattern.toCharArray()) {
count++;
if
(count ==
1
)
distinct++;
}
int
currCount =
0
;
for
(
int
i =
0
; i < str.length(); i++) {
count[str.charAt(i)]--;
if
(count[str.charAt(i)] ==
0
) {
currCount++;
}
if
(i >= mid) {
count[str.charAt(i - mid)]++;
if
(count[str.charAt(i - mid)] ==
1
) {
currCount--;
}
}
if
(i >= mid -
1
) {
if
(currCount == distinct) {
found =
true
;
start[
0
] = (i - mid) +
1
;
break
;
}
}
}
return
found;
}
static
String findSmallestSubstring(String str, String pattern) {
int
lenStr = str.length();
int
lenPattern = pattern.length();
String smallestSubstring =
""
;
int
minLength = Integer.MAX_VALUE;
int
lowBound =
1
, highBound = lenStr;
int
[] idx =
new
int
[
1
];
while
(lowBound <= highBound) {
int
mid = (lowBound + highBound) /
2
;
int
[] start =
new
int
[
1
];
if
(isValid(str, pattern, mid, start)) {
if
(mid < minLength) {
minLength = mid;
idx[
0
] = start[
0
];
}
highBound = mid -
1
;
}
else
{
lowBound = mid +
1
;
}
}
return
smallestSubstring = str.substring(idx[
0
], idx[
0
] + minLength);
}
public
static
void
main(String[] args) {
String str1 =
"this is a test string"
;
String pattern1 =
"tist"
;
System.out.println(
"Input: string = \""
+ str1
+
"\", pattern = \""
+ pattern1 +
"\""
);
System.out.println(
"Output: \""
+ findSmallestSubstring(str1, pattern1) +
"\""
);
String str2 =
"geeksforgeeks"
;
String pattern2 =
"ork"
;
System.out.println(
"Input: string = \""
+ str2
+
"\", pattern = \""
+ pattern2 +
"\""
);
System.out.println(
"Output: \""
+ findSmallestSubstring(str2, pattern2) +
"\""
);
}
}