I want to find a single regex which matches the longest numerical string in a URL.
I.e for the URL: http://stackoverflow.com/1234/questions/123456789/ask, I would like it to return : 123456789
I thought I could use : ([\d]+)
However this returns the first match from the left, not the longest.
Any ideas :) ?
This regex will be used as an input to a strategy pattern, which extracts certain characteristics from urls:
public static String parse(String url, String RegEx) {
Pattern pattern = Pattern.compile(regex);
Matcher m = pattern.matcher(url);
if (m.find()) {
return m.group(1);
}
return null;
}
So it would be much tidier if I could use a single regex. :( –
Don't use regex. Just iterate the characters:
String longest = 0;
int i = 0;
while (i < str.length()) {
while (i < str.length() && !Character.isDigit(str.charAt(i))) {
++i;
}
int start = i;
while (i < str.length() && Character.isDigit(str.charAt(i))) {
++i;
}
if (i - start > longest.length()) {
longest = str.substring(start, i);
}
}
#Andy already gave a non-regex answer, which is probably faster, but if you want to use regex, you must, as #Jan points out, add logic, e.g.:
public String findLongestNumber(String input) {
String longestMatch = "";
int maxLength = 0;
Matcher m = Pattern.compile("([\\d]+)").matcher(input);
while (m.find()) {
String currentMatch = m.group();
int currentLength = currentMatch.length();
if (currentLength > maxLength) {
maxLength = currentLength;
longestMatch = currentMatch;
}
}
return longestMatch;
}
t
Not possible with pure Regex, however I would do it this way (using Stream Max and Regex) :
String url = "http://stackoverflow.com/1234/questions/123456789/ask";
Pattern biggest = Pattern.compile("/(\\d+)/");
Matcher m = biggest.matcher(url);
List<String> matches = new ArrayList<>();
while(m.find()){
matches.add(m.group(1));
}
System.out.println(matches.parallelStream().max((String a, String b) -> Integer.compare(a.length(), b.length())).get());
Will print : 123456789
I have some string data that have some pattern like this:
"0x4F 0xBB 0x74 0xA9"
It has four parts.
Each part has three or four chars.
Each part begins with 0x.
Among the parts we have space.
Character just: A B C D E F
Numbers: 0-9
** i want to return this pattern as string ! how to return it ?
assume that sample input string that i get it, is :
"vhmbjfbfbbdbd This is part of my String 0x4F 0xBB 0x74 0xA9 and rest afhahjbsdvbskb"
how to return this string after matching: "0x4F 0xBB 0x74 0xA9"
String MP = MatchedPart(str).toString();
private static StringBuilder MatchedPart(String s) {
List<String> sarr = Arrays.asList(s.split(" 0x[A-F0-9]{1,2} 0x[A-F0-9]{1,2} 0x[A-F0-9]{1,2} 0x[A-F0-9]{1,2}"));
StringBuilder machpart = new StringBuilder();
for(String t : sarr) {
machpart = machpart.append(t) ;
}
return machpart ;
}
I write this function that gets a string and check pattern:
public static boolean test (String s) {
Pattern pattern = Pattern.compile(" 0x[ABCDEF0-9] 0x[ABCDEF0-9] 0x[ABCDEF0-9] 0x[ABCDEF0-9]");
Matcher matcher = pattern.matcher(s);
if (matcher.find()){
return true;
}
return false;
}
According to your question just use like as below:
public class PatternIncorrect {
public static void main(String[] args) {
System.out.println("------Test 1------------- ");
System.out.println(test1("0x4F 0xBB 0x74 0xA9"));
System.out.println("------Test 2--------------");
System.out.println(test2("0x4F 0xBB 0x74 0xA9"));
System.out.println("------Test 3--------------");
List<String> test3 = test3("0x4F 0xBB 0x74 0xA9asdasd0x4F 0xBB 0x74 0xA9mfdskf0x4F 0xBB 0x74 0xA9");
for(String t : test3) {
System.out.println(t);
}
}
public static boolean test1(String str) {
List<String> strings = Arrays.asList(str.split(" "));
boolean isMatch = true;
String regEx = "0x[1-9][ABCDEF]|0x[ABCDEF][1-9]|0x[1-9][1-9]|0x[ABCDEF][ABCDEF]";
for (String s : strings) {
if (!s.matches(regEx)) {
System.out.println(s);
isMatch = false;
break;
}
}
return isMatch;
}
public static boolean test2(String s) {
String regEx = "0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2}";
Pattern pattern = Pattern.compile(regEx);
Matcher matcher = pattern.matcher(s);
return matcher.find();
}
public static List<String> test3(String s) {
String regEx = "0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2}";
return Arrays.asList(s.split(regEx));
}
}
Source Code On enter link description here
Try
Pattern pattern = Pattern.compile(" 0x[ABCDEF1-9]{1,2} 0x[ABCDEF1-9]{1,2} 0x[ABCDEF1-9]{1,2} 0x[ABCDEF1-9]{1,2}");
If you want to be a bit more familiar with regex in Java, read : https://docs.oracle.com/javase/tutorial/essential/regex/index.html
Your expression starts with a white space, which, from what I am seeing, your input string does not.
Also, and more importantly, according to your description you are attempting to match 3 or 4 characters, but according to your expression you are always expecting 3.
Replace Pattern pattern = Pattern.compile(" 0x[ABCDEF1-9] 0x[ABCDEF1-9] 0x[ABCDEF1-9] 0x[ABCDEF1-9]"); with Pattern pattern = Pattern.compile("0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2} 0x[A-F1-9]{1,2}"); and it should work.
For the record, 0x00 should also be a valid hexadecimal number, which your expression would seem to not consider as valid.
You can replace [ABCDEF1-9] with the predefined pattern \p{XDigit}
another suggestion:
Scanner sc = new Scanner(s);
int count = 0;
while(sc.hasNextInt(16)){
sc.nextInt(16);
count++;
}
return count == 4;
I need a regular expression to do the following:
I have this String: 123.45.678.7 and I need to replace all (.) characters from the second. The result will be 123.456787
¿Can anyone help me please?
System.out.println(
"123.45.678.7".replaceAll("\\G((?!^).*?|[^\\.]*\\..*?)\\.", "$1"));
123.456787
This can also be done without a regular expression:
String str = "123.45.678.7";
String[] arr = str.split("\\.", 2);
System.out.println(arr[0] + "." + arr[1].replace(".", ""));
123.456787
This code matches all of the periods with a regular expression, then puts the first decimal point back in the String.
Here are the test results:
123.45.678.7, 123.456787
And here's the code.
public class SecondMatch {
public String match(String s) {
StringBuilder builder = new StringBuilder();
String[] parts = s.split("\\.");
for (int i = 0; i < parts.length; i++) {
builder.append(parts[i]);
if (i == 0) {
builder.append(".");
}
}
return builder.toString();
}
public static void main(String[] args) {
String s = "123.45.678.7";
String t = new SecondMatch().match(s);
System.out.println(s + ", " + t);
}
}
Just create a function...
function removeAllButFirst(myParam)
{
var numReplaces = 0;
var retVal = myParam.replace(/\./g, function(allMatch, currMatch) {
return ++numReplaces==1 ? '.' : ''; });
return retVal;
}
Just had a rummage and found this on the net - its fairly crude, but would do the job...
retVal = retVal.replaceFirst(".","$");
retVal = retVal.replaceAll(".","");
retVal = retVal.replaceFirst("$",".");
This does assume you don't have any $'s in your input - if you do pick a different char.
Its not great and there is probably a better single regex on Java using something like LookBehinds but I'm not a Java dev so couldnt say.
This regex should also work:
String str = "123.45.678.9";
String repl = str.replaceAll("([^.]*\\.[^.]*|[^.]*)\\.", "$1");
// repl = 123.456789
I have a string,
String s = "test string (67)";
I want to get the no 67 which is the string between ( and ).
Can anyone please tell me how to do this?
There's probably a really neat RegExp, but I'm noob in that area, so instead...
String s = "test string (67)";
s = s.substring(s.indexOf("(") + 1);
s = s.substring(0, s.indexOf(")"));
System.out.println(s);
A very useful solution to this issue which doesn't require from you to do the indexOf is using Apache Commons libraries.
StringUtils.substringBetween(s, "(", ")");
This method will allow you even handle even if there multiple occurrences of the closing string which wont be easy by looking for indexOf closing string.
You can download this library from here:
https://mvnrepository.com/artifact/org.apache.commons/commons-lang3/3.4
Try it like this
String s="test string(67)";
String requiredString = s.substring(s.indexOf("(") + 1, s.indexOf(")"));
The method's signature for substring is:
s.substring(int start, int end);
By using regular expression :
String s = "test string (67)";
Pattern p = Pattern.compile("\\(.*?\\)");
Matcher m = p.matcher(s);
if(m.find())
System.out.println(m.group().subSequence(1, m.group().length()-1));
Java supports Regular Expressions, but they're kind of cumbersome if you actually want to use them to extract matches. I think the easiest way to get at the string you want in your example is to just use the Regular Expression support in the String class's replaceAll method:
String x = "test string (67)".replaceAll(".*\\(|\\).*", "");
// x is now the String "67"
This simply deletes everything up-to-and-including the first (, and the same for the ) and everything thereafter. This just leaves the stuff between the parenthesis.
However, the result of this is still a String. If you want an integer result instead then you need to do another conversion:
int n = Integer.parseInt(x);
// n is now the integer 67
In a single line, I suggest:
String input = "test string (67)";
input = input.subString(input.indexOf("(")+1, input.lastIndexOf(")"));
System.out.println(input);`
You could use apache common library's StringUtils to do this.
import org.apache.commons.lang3.StringUtils;
...
String s = "test string (67)";
s = StringUtils.substringBetween(s, "(", ")");
....
Test String test string (67) from which you need to get the String which is nested in-between two Strings.
String str = "test string (67) and (77)", open = "(", close = ")";
Listed some possible ways: Simple Generic Solution:
String subStr = str.substring(str.indexOf( open ) + 1, str.indexOf( close ));
System.out.format("String[%s] Parsed IntValue[%d]\n", subStr, Integer.parseInt( subStr ));
Apache Software Foundation commons.lang3.
StringUtils class substringBetween() function gets the String that is nested in between two Strings. Only the first match is returned.
String substringBetween = StringUtils.substringBetween(subStr, open, close);
System.out.println("Commons Lang3 : "+ substringBetween);
Replaces the given String, with the String which is nested in between two Strings. #395
Pattern with Regular-Expressions: (\()(.*?)(\)).*
The Dot Matches (Almost) Any Character
.? = .{0,1}, .* = .{0,}, .+ = .{1,}
String patternMatch = patternMatch(generateRegex(open, close), str);
System.out.println("Regular expression Value : "+ patternMatch);
Regular-Expression with the utility class RegexUtils and some functions.
Pattern.DOTALL: Matches any character, including a line terminator.
Pattern.MULTILINE: Matches entire String from the start^ till end$ of the input sequence.
public static String generateRegex(String open, String close) {
return "(" + RegexUtils.escapeQuotes(open) + ")(.*?)(" + RegexUtils.escapeQuotes(close) + ").*";
}
public static String patternMatch(String regex, CharSequence string) {
final Pattern pattern = Pattern.compile(regex, Pattern.DOTALL);
final Matcher matcher = pattern .matcher(string);
String returnGroupValue = null;
if (matcher.find()) { // while() { Pattern.MULTILINE }
System.out.println("Full match: " + matcher.group(0));
System.out.format("Character Index [Start:End]«[%d:%d]\n",matcher.start(),matcher.end());
for (int i = 1; i <= matcher.groupCount(); i++) {
System.out.println("Group " + i + ": " + matcher.group(i));
if( i == 2 ) returnGroupValue = matcher.group( 2 );
}
}
return returnGroupValue;
}
String s = "test string (67)";
int start = 0; // '(' position in string
int end = 0; // ')' position in string
for(int i = 0; i < s.length(); i++) {
if(s.charAt(i) == '(') // Looking for '(' position in string
start = i;
else if(s.charAt(i) == ')') // Looking for ')' position in string
end = i;
}
String number = s.substring(start+1, end); // you take value between start and end
String result = s.substring(s.indexOf("(") + 1, s.indexOf(")"));
public String getStringBetweenTwoChars(String input, String startChar, String endChar) {
try {
int start = input.indexOf(startChar);
if (start != -1) {
int end = input.indexOf(endChar, start + startChar.length());
if (end != -1) {
return input.substring(start + startChar.length(), end);
}
}
} catch (Exception e) {
e.printStackTrace();
}
return input; // return null; || return "" ;
}
Usage :
String input = "test string (67)";
String startChar = "(";
String endChar = ")";
String output = getStringBetweenTwoChars(input, startChar, endChar);
System.out.println(output);
// Output: "67"
Another way of doing using split method
public static void main(String[] args) {
String s = "test string (67)";
String[] ss;
ss= s.split("\\(");
ss = ss[1].split("\\)");
System.out.println(ss[0]);
}
Use Pattern and Matcher
public class Chk {
public static void main(String[] args) {
String s = "test string (67)";
ArrayList<String> arL = new ArrayList<String>();
ArrayList<String> inL = new ArrayList<String>();
Pattern pat = Pattern.compile("\\(\\w+\\)");
Matcher mat = pat.matcher(s);
while (mat.find()) {
arL.add(mat.group());
System.out.println(mat.group());
}
for (String sx : arL) {
Pattern p = Pattern.compile("(\\w+)");
Matcher m = p.matcher(sx);
while (m.find()) {
inL.add(m.group());
System.out.println(m.group());
}
}
System.out.println(inL);
}
}
The "generic" way of doing this is to parse the string from the start, throwing away all the characters before the first bracket, recording the characters after the first bracket, and throwing away the characters after the second bracket.
I'm sure there's a regex library or something to do it though.
The least generic way I found to do this with Regex and Pattern / Matcher classes:
String text = "test string (67)";
String START = "\\("; // A literal "(" character in regex
String END = "\\)"; // A literal ")" character in regex
// Captures the word(s) between the above two character(s)
String pattern = START + "(\w+)" + END;
Pattern pattern = Pattern.compile(pattern);
Matcher matcher = pattern.matcher(text);
while(matcher.find()) {
System.out.println(matcher.group()
.replace(START, "").replace(END, ""));
}
This may help for more complex regex problems where you want to get the text between two set of characters.
The other possible solution is to use lastIndexOf where it will look for character or String from backward.
In my scenario, I had following String and I had to extract <<UserName>>
1QAJK-WKJSH_MyApplication_Extract_<<UserName>>.arc
So, indexOf and StringUtils.substringBetween was not helpful as they start looking for character from beginning.
So, I used lastIndexOf
String str = "1QAJK-WKJSH_MyApplication_Extract_<<UserName>>.arc";
String userName = str.substring(str.lastIndexOf("_") + 1, str.lastIndexOf("."));
And, it gives me
<<UserName>>
String s = "test string (67)";
System.out.println(s.substring(s.indexOf("(")+1,s.indexOf(")")));
Something like this:
public static String innerSubString(String txt, char prefix, char suffix) {
if(txt != null && txt.length() > 1) {
int start = 0, end = 0;
char token;
for(int i = 0; i < txt.length(); i++) {
token = txt.charAt(i);
if(token == prefix)
start = i;
else if(token == suffix)
end = i;
}
if(start + 1 < end)
return txt.substring(start+1, end);
}
return null;
}
This is a simple use \D+ regex and job done.
This select all chars except digits, no need to complicate
/\D+/
it will return original string if no match regex
var iAm67 = "test string (67)".replaceFirst("test string \\((.*)\\)", "$1");
add matches to the code
String str = "test string (67)";
String regx = "test string \\((.*)\\)";
if (str.matches(regx)) {
var iAm67 = str.replaceFirst(regx, "$1");
}
---EDIT---
i use https://www.freeformatter.com/java-regex-tester.html#ad-output to test regex.
turn out it's better to add ? after * for less match. something like this:
String str = "test string (67)(69)";
String regx1 = "test string \\((.*)\\).*";
String regx2 = "test string \\((.*?)\\).*";
String ans1 = str.replaceFirst(regx1, "$1");
String ans2 = str.replaceFirst(regx2, "$1");
System.out.println("ans1:"+ans1+"\nans2:"+ans2);
// ans1:67)(69
// ans2:67
String s = "(69)";
System.out.println(s.substring(s.lastIndexOf('(')+1,s.lastIndexOf(')')));
Little extension to top (MadProgrammer) answer
public static String getTextBetween(final String wholeString, final String str1, String str2){
String s = wholeString.substring(wholeString.indexOf(str1) + str1.length());
s = s.substring(0, s.indexOf(str2));
return s;
}
Is it possible to make String.replaceAll put the number (count) of the current replacement into the replacement being made?
So that "qqq".replaceAll("(q)", "something:$1 ") would result in "1:q 2:q 3:q"?
Is there anything that I can replace something in the code above with, to make it resolve into the current substitution count?
Here is one way of doing this:
StringBuffer resultString = new StringBuffer();
String subjectString = new String("qqqq");
Pattern regex = Pattern.compile("q");
Matcher regexMatcher = regex.matcher(subjectString);
int i = 1;
while (regexMatcher.find()) {
regexMatcher.appendReplacement(resultString, i+":"+regexMatcher.group(1)+" ");
i++;
}
regexMatcher.appendTail(resultString);
System.out.println(resultString);
See it
No, not with the replaceAll method. The only backreference is \n where n is the n'th capturing group matched.
For this you have to create your own replaceAll() method.
This helps you:
public class StartTheClass
{
public static void main(String[] args)
{
String string="wwwwww";
System.out.println("Replaced As: \n"+replaceCharector(string, "ali:", 'w'));
}
public static String replaceCharector(String original, String replacedWith, char toReplaceChar)
{
int count=0;
String str = "";
for(int i =0; i < original.length(); i++)
{
if(original.charAt(i) == toReplaceChar)
{
str += replacedWith+(count++)+" ";//here add the 'count' value and some space;
}
else
{
str += original.charAt(i);
}
}
return str;
}
}
The output I got is:
Replaced As:
ali:0 ali:1 ali:2 ali:3 ali:4 ali:5