The PCRE-compatible regex to match this would be:
/([\s.',-])\1+/
If you're using Perl, you can replace it using the following expression:
s/([\s.',-])\1+/$1/g
If you're using PHP, then you would use this syntax:
$out = preg_replace('/([\s.\',-])\1+/', '$1', $in);
Explanation
- The
()group matches the single character, in this case either a whitespace character (\s) or the punctuation characters (. ' - ,). It's good practice to put-at the end of the list inside[]. - The
\1means that the same thing it just matched in the parentheses occurs at least once more. - In the replacement, the
$1refers to the match in first set of parentheses.
Note: this is Perl-Compatible Regular Expression (PCRE) syntax.
From the perlretut man page:
Answer from amphetamachine on Stack OverflowMatching repetitions
The examples in the previous section display an annoying weakness. We were only matching 3-letter words, or chunks of words of 4 letters or less. We'd like to be able to match words or, more generally, strings of any length, without writing out tedious alternatives like
\w\w\w\w|\w\w\w|\w\w|\w.This is exactly the problem the quantifier metacharacters
?,*,+, and{}were created for. They allow us to delimit the number of repeats for a portion of a regexp we consider to be a match. Quantifiers are put immediately after the character, character class, or grouping that we want to specify. They have the following meanings:
a?means: match 'a' 1 or 0 times
a*means: match 'a' 0 or more times, i.e., any number of times
a+means: match 'a' 1 or more times, i.e., at least once
a{n,m}means: match at least "n" times, but not more than "m" times.
a{n,}means: match at least "n" or more times
a{n}means: match exactly "n" times
The PCRE-compatible regex to match this would be:
/([\s.',-])\1+/
If you're using Perl, you can replace it using the following expression:
s/([\s.',-])\1+/$1/g
If you're using PHP, then you would use this syntax:
$out = preg_replace('/([\s.\',-])\1+/', '$1', $in);
Explanation
- The
()group matches the single character, in this case either a whitespace character (\s) or the punctuation characters (. ' - ,). It's good practice to put-at the end of the list inside[]. - The
\1means that the same thing it just matched in the parentheses occurs at least once more. - In the replacement, the
$1refers to the match in first set of parentheses.
Note: this is Perl-Compatible Regular Expression (PCRE) syntax.
From the perlretut man page:
Matching repetitions
The examples in the previous section display an annoying weakness. We were only matching 3-letter words, or chunks of words of 4 letters or less. We'd like to be able to match words or, more generally, strings of any length, without writing out tedious alternatives like
\w\w\w\w|\w\w\w|\w\w|\w.This is exactly the problem the quantifier metacharacters
?,*,+, and{}were created for. They allow us to delimit the number of repeats for a portion of a regexp we consider to be a match. Quantifiers are put immediately after the character, character class, or grouping that we want to specify. They have the following meanings:
a?means: match 'a' 1 or 0 times
a*means: match 'a' 0 or more times, i.e., any number of times
a+means: match 'a' 1 or more times, i.e., at least once
a{n,m}means: match at least "n" times, but not more than "m" times.
a{n,}means: match at least "n" or more times
a{n}means: match exactly "n" times
As others said it depends on you regex engine but a small example how you could do this:
/([ _-,.])\1*/\1/g
With sed:
$ echo "foo , bar" | sed 's/\([ _-,.]\)\1*/\1/g'
foo , bar
$ echo "foo,. bar" | sed 's/\([ _-,.]\)\1*/\1/g'
foo,. bar
$ tr -s '[:lower:]' <<<"staaacksoveerfloow"
stacksoverflow
The tr utility is used here with its -s option to remove consecutive duplicates of any lowercase character in the given string.
In place of [:lower:], you could use a-z or any range or character class that matches the characters that you want to affect.
you can use sed for that
echo staaacksoveerfloow | sed 's/\([a-zA-Z]\)\1\+/\1/g'
and I think the question is a dup―not dup state. you can refer more in here
java - Regex to replace repeated characters - Stack Overflow
How to replace any number of repeating characters in a string or character array
Regex to match repeating characters
java - Replace multiple occurrences of a character - Code Review Stack Exchange
Change your regex like below.
string.replaceAll("((.)\\2{2})\\2+","$1");
(start of the first caturing group.(.)captures any character. For this case, you may use[a-z]\\2refers the second capturing group.\\2{2}which must be repeated exactly two times.)End of first capturing group. So this would capture the first three repeating characters.\\2+repeats the second group one or more times.
DEMO
I think you might want something like this:
str.replaceAll("([a-zA-Z])\\1\\1+", "
1$1");
This will match where a character is repeated 3 or more times and will replace it with the same character, three times.
$1 only matches one character, because you're surrounding the character to match.
\\1\\1+ matches the character only, if it occurs at least three times in a row.
This call is also a lot more readable, than having a huge regex and only using one $1.
I think this is oddly complicated...though, I'm 99% sure this can be done with a single line of RegEx, I don't know how from the top of my head1.
This can be shortened to a much simpler and shorter solution, without the need of arrays at all.
String input = "hhiii!!! hooowww aaareee yyyooou???";
StringBuilder output = new StringBuilder();
// Append the first character of the string.
// We can also let the loop start at 0, but then
// we'd need an additional if inside the loop, which
// I'd like to avoid.
output.append(input.charAt(0));
// Start the loop at 1, because we already have the first character.
// We can not
for (int idx = 1; idx < input.length(); idx++) {
// Check the current against the previous character.
if(input.charAt(idx) != input.charAt(idx-1)) {
// If it is not the same, append it.
output.append(input.charAt(idx));
}
}
Of course you'd need to protect yourself from invalid input (empty or null String), and it will also break words with allowed double-characters: foobar, tool, support etc..
Some further comments on your code:
- Function name: It's not directly visible what the function does. It should be called something along the lines of
removeDoubleCharsorremoveMultipleCharacters. - Function type: The function shouldn't directly output the result to
System.outbut rather return it. - Loops: Use appropriate loops, f.e. your
whileshould be afor. - Variable names: I know it's partly taught, but I get the creeps (or become a Creeper) if I see variables which are named
i,jorarr. Give your variables meaningful names! In any modern language the name of the variable is neither limited nor does it matter for performance. Write your code primarily for humans, and only secondary for machines...the coder which has to maintain your code after you will thank you. - Whitespaces: Use 'em!
if(str.charAt(i)!=str.charAt(i+1)){is harder to read thenif(str.charAt(i) != str.charAt(i + 1)) {. - Code duplication: Avoid duplicate code. In this case it's minor, but the
i++should be moved outside theif, so that it's not necessary to have anelsepart.
1: But John does.
Maybe I am wrong but I prefers to use the regex for this kind of text manipulation.
Here is my code,
System.out.println("hhiii!!! hooowww aaareee yyyooou???"
.replaceAll("(.)\\1+","$1"));
I have a situation where there are multiple periods from string (i.e. Hello.......)
I am attempting to create a REPLACE to look for any instance where there are multiple periods, and replace with just one.
'Hello.......' would be 'Hello.'
text = 'Hello.......'
text = Regex.Replace(text, ".{2,}", ".")
But this doesnt seem to work..
Any assistance is appreciated.
Change it to:
string = string.replace(/-{2,}/g,"-");
Another way is
string = string.replace(/-+/g,"-");
as that replaces any one or more instances of - with only one -.
{2} matches exactly two, + matches one or more.
string = string.replace(/\-+/g, '-');
For more on RegEx, See the MDN documentation
- Ctrl+H
- Find what:
^(\w+,\h*)(\w+)(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))?(?:,\h*(\w+))? - Replace with:
$1$2\n(?3$1$3)(?4\n$1$4)(?5\n$1$5)(?6\n$1$6)(?7\n$1$7)(?8\n$1$8)(?9\n$1$9) - TICK Match case
- TICK Wrap around
- SELECT Regular expression
- UNTICK
. matches newline - Replace all
Explanation:
^ # beginning of line
( # group 1
\w+ # 1 or more word characters
, # a comma
\h* # 0 or more horizontal spaces
) # end group 1
(\w+) # group 2, 1 or more word characters
(?: # non capture group
\h* # 0 or more horizontal spaces
(\w+) # group 3, 1 or more word characters
)? # end group, optional
(?:,\h*(\w+))? # same as above
(?:,\h*(\w+))? # same as above
(?:,\h*(\w+))? # same as above
(?:,\h*(\w+))? # ...
(?:,\h*(\w+))? # ...
(?:,\h*(\w+))? # ...
(?:,\h*(\w+))? # ...
(?:,\h*(\w+))? # ...
Replacement:
$1 # content of group 1
$2 # content of group 2
\n # line feed, you can use \r\n for Windows
(?3 # if group 3 exists
$1 # content of group 1
$3 # content of group 3
) # endif
(?4\n$1$4) # same as above
(?5\n$1$5) # ...
(?6\n$1$6) # ...
(?7\n$1$7) # ...
(?8\n$1$8) # ...
(?9\n$1$9) # ...
Screenshot (before):

Screenshot (after):

That regex is way too complicated. By using an actual programming language, things will be much simpler.
Here I give an example in Python. Get Python here.
Say you have this input:
Chicago, ORD, MDW
NY, JFK, LGA, EWR
California, LAX, JWA, LGB, BUR
And you want to convert it to your given output:
Chicago, ORD
Chicago, MDW
NY, JFK
NY, LGA
NY, EWR
California, LAX
California, JWA
California, LGB
California, BUR
It is simple, first split the string into lines, the split each line into list of strings by commas. Finally return the combination of the first element and every other element of the same list.
lines = """Chicago, ORD, MDW
NY, JFK, LGA, EWR
California, LAX, JWA, LGB, BUR"""
for line in lines.splitlines():
lst = line.split(', ')
first = lst[0]
for e in lst[1:]:
print(f'{first}, {e}')