-
-
Notifications
You must be signed in to change notification settings - Fork 2.2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Refactor
is_subsequence
Implemenation (#819)
ref: refactor is subsequence implemenation
- Loading branch information
Showing
1 changed file
with
58 additions
and
20 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,33 +1,71 @@ | ||
// Given two strings str1 and str2, return true if str1 is a subsequence of str2, or false otherwise. | ||
// A subsequence of a string is a new string that is formed from the original string | ||
// by deleting some (can be none) of the characters without disturbing the relative | ||
// positions of the remaining characters. | ||
// (i.e., "ace" is a subsequence of "abcde" while "aec" is not). | ||
pub fn is_subsequence(str1: &str, str2: &str) -> bool { | ||
let mut it1 = 0; | ||
let mut it2 = 0; | ||
//! A module for checking if one string is a subsequence of another string. | ||
//! | ||
//! A subsequence is formed by deleting some (can be none) of the characters | ||
//! from the original string without disturbing the relative positions of the | ||
//! remaining characters. This module provides a function to determine if | ||
//! a given string is a subsequence of another string. | ||
|
||
let byte1 = str1.as_bytes(); | ||
let byte2 = str2.as_bytes(); | ||
/// Checks if `sub` is a subsequence of `main`. | ||
/// | ||
/// # Arguments | ||
/// | ||
/// * `sub` - A string slice that may be a subsequence. | ||
/// * `main` - A string slice that is checked against. | ||
/// | ||
/// # Returns | ||
/// | ||
/// Returns `true` if `sub` is a subsequence of `main`, otherwise returns `false`. | ||
pub fn is_subsequence(sub: &str, main: &str) -> bool { | ||
let mut sub_iter = sub.chars().peekable(); | ||
let mut main_iter = main.chars(); | ||
|
||
while it1 < str1.len() && it2 < str2.len() { | ||
if byte1[it1] == byte2[it2] { | ||
it1 += 1; | ||
while let Some(&sub_char) = sub_iter.peek() { | ||
match main_iter.next() { | ||
Some(main_char) if main_char == sub_char => { | ||
sub_iter.next(); | ||
} | ||
None => return false, | ||
_ => {} | ||
} | ||
|
||
it2 += 1; | ||
} | ||
|
||
it1 == str1.len() | ||
true | ||
} | ||
|
||
#[cfg(test)] | ||
mod tests { | ||
use super::*; | ||
|
||
#[test] | ||
fn test() { | ||
assert!(is_subsequence("abc", "ahbgdc")); | ||
assert!(!is_subsequence("axc", "ahbgdc")); | ||
macro_rules! subsequence_tests { | ||
($($name:ident: $test_case:expr,)*) => { | ||
$( | ||
#[test] | ||
fn $name() { | ||
let (sub, main, expected) = $test_case; | ||
assert_eq!(is_subsequence(sub, main), expected); | ||
} | ||
)* | ||
}; | ||
} | ||
|
||
subsequence_tests! { | ||
test_empty_subsequence: ("", "ahbgdc", true), | ||
test_empty_strings: ("", "", true), | ||
test_non_empty_sub_empty_main: ("abc", "", false), | ||
test_subsequence_found: ("abc", "ahbgdc", true), | ||
test_subsequence_not_found: ("axc", "ahbgdc", false), | ||
test_longer_sub: ("abcd", "abc", false), | ||
test_single_character_match: ("a", "ahbgdc", true), | ||
test_single_character_not_match: ("x", "ahbgdc", false), | ||
test_subsequence_at_start: ("abc", "abchello", true), | ||
test_subsequence_at_end: ("cde", "abcde", true), | ||
test_same_characters: ("aaa", "aaaaa", true), | ||
test_interspersed_subsequence: ("ace", "abcde", true), | ||
test_different_chars_in_subsequence: ("aceg", "abcdef", false), | ||
test_single_character_in_main_not_match: ("a", "b", false), | ||
test_single_character_in_main_match: ("b", "b", true), | ||
test_subsequence_with_special_chars: ("a1!c", "a1!bcd", true), | ||
test_case_sensitive: ("aBc", "abc", false), | ||
test_subsequence_with_whitespace: ("hello world", "h e l l o w o r l d", true), | ||
} | ||
} |