Building a pattern to extract data out of a string - java

I have strings of the form:
"abc" 1 2 1 13
"efgh" 2 5
Basically, a string in quotes followed by numbers separated by whitespace characters.
I need to extract the string and the numbers out of the line.
So for eg., for the first line, I'd want
abc to be stored in a String variable (i.e. without the quotations) and
an array of int to store [1,2,1,13].
I tried to create a pattern that'd do this, but I'm a little confused.
Pattern P = Pattern.compile("\A\".+\"(\s\d+)+");
Not sure how to proceed now. I realized that with this pattern I'd kinda be extracting the whole line out? Perhaps multiple patterns would help?
Pattern P1 = Pattern.compile("\A\".+\"");
Pattern P2 = Pattern.compile("(\s\d+)+");
Again, not very sure how to get the string and ints out of the line though. Any help is appreciated!

I would rather just split the string on space, rather than building complex regex, and use it with Pattern and Matcher class.
Something like this: -
String str = "\"abc\" 1 2 1 13 ";
String[] arrr = str.split("\\s");
System.out.println(Arrays.toString(arrr));
OUTPUT: -
["abc", 1, 2, 1, 13]
Shows your intent much clearer, that what you want to do.
Then, you can get the string and integer parts from your string array. You would need to do a Integer.parseInt() on integer elements.
If your string may contain spaces in it, then in that case, you would need a Regex. Better one would be the one in #m.buettner's answer

Use capturing groups to get both parts in one go, then split the numbers at spaces.
Pattern pattern = Pattern.compile("\"([^\"]*)\"\\s*([\\d\\s]*)");
Matcher m = pattern .matcher(input);
while (m.find()) {
String str = m.group(1);
String[] numbers = m.group(2).split("\\s");
// process both of them
}
Each set of parentheses in the regex will later correspond to one group (counting opening parentheses from left to right, starting at 1).

Please try this it will separate both String and int also
String s = "\"abc\" 1 2 1 13 ";
s = s.replace("\"", "");
String sarray[] = s.split(" ");
int i[] = new int[10];
String si[] = new String[10];
int siflag = 0;
int iflag = 0;
for (String st : sarray) {
try {
int ii = Integer.parseInt(st)
i[iflag++] = ii;
} catch (NumberFormatException e) {
si[siflag++] = st;
}
}

StringTokenizer st = new StringTokenizer(str,"\" ");
String token = null;
String strComponent = null;
int num[] = new int[10]; // can change length dynamically by using ArrayList
int i = 0;
int numTemp = -1;
while(st.hasMoreTokens()){
token = st.nextToken();
try{
numTemp = Integer.parseInt(token);
num[i++] = numTemp ;
}catch(NumberFormatException nfe){
strComponent = token.toString();
}

Related

Get certain substring from String java

I can have this string as below :
String s = "chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
or
String s = "chapterId=c_1&sectionId=s_24666";
I need to get the number ("24666" in the examples).
String res = s.substring(s.lastIndexOf("s_")+ 2) this returns me the number + chars till the end of the string(the second example is ok). But I need to stop after the number ends. How can I do that.? Thanks
You can use regExp
String s = "chapterId=c_1&sectionId=s_24666";
//OR
//String s = "chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
s=s.replaceAll(".*?s_(\\d+).*","$1");
System.out.println(s);
OUTPUT:
24666
Where,
.*?s_ means anything before s_ (s_ inclusive)
(\\d+) means one or more digits () used for group
$1 means group 1 which is digits after s_
Note:Assumed that your every string follows specific format which includes s_ and number after s_.
You can split the string by the character & to get the parameters, and split each parameter with the = to get the parameter name and parameter value. And now look for the parameter name "sectionId", and cut the first 2 characters of its value to get the number, and you can use Integer.parseInt() if you need it as an int.
Note that this solution is flexible enough to process all parameters, not just the one you're currently interested in:
String s = "chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
String[] params = s.split("&");
for (String param : params) {
String[] nameValue = param.split("=");
if ("sectionId".equals(nameValue[0])) {
int number = Integer.parseInt(nameValue[1].substring(2));
System.out.println(number); // Prints 24666
// If you don't care about other parameters, this will skip the rest:
break;
}
}
Note:
You might want to put Integer.parseInt() into a try-catch block in case an invalid number would be passed from the client:
try {
int number = Integer.parseInt(nameValue[1].substring(2));
} catch (Exception e) {
// Invalid parameter value, not the expected format!
}
Try this:
I use a check in the substring() method - if there is no "&isHL" in the string (meaning its type 2 you showed us), it will just read until the string ends. otherwise, it will cut the string before the "&isHL". Hope this helps.
Code:
String s = "chapterId=c_1&sectionId=s_**24666**";
int endIndex = s.indexOf("&isHL");
String answer = s.substring(s.lastIndexOf("s_") + 2, endIndex == -1 ? s.length() : endIndex);
Try following:
String s = "chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
String tok[]=s.split("&");
for(String test:tok){
if(test.contains("s_")){
String next[]=test.split("s_");
System.out.println(next[1]);
}
}
Output :
24666
Alternatively you can simply remove all other words if they are not required as below
String s="chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
s=s.replaceAll(".*s_(\\d+).*","$1");
System.out.println(s);
Output :
24666
The dig over here is splitting your string using a Regular Expression to further divide the string into parts and get what is required. For more on Regular Expressions visit this link.
You could sue this regex : (?<=sectionId=s_)(\\d+) This uses positive look-behind.
demo here
Following code will work even if there is multiple occurrence of integer in given string
String inputString = "chapterId=c_a&sectionId=s_24666&isHL=1&cssFileName=haynes_45";
String[] inputParams = inputString.split("&");
for (String param : inputParams)
{
String[] nameValue = param.split("=");
try {
int number = Integer.parseInt(getStringInt(nameValue[1]));
System.out.println(number);
}
catch(IllegalStateException illegalStateException){
}
}
private String getStringInt(String inputString)
{
Pattern onlyInt = Pattern.compile("\\d+");
Matcher matcher = onlyInt.matcher(inputString);
matcher.find();
String inputInt = matcher.group();
return inputInt;
}
OUTPUT
2466
1
45
Use split method as
String []result1 = s.split("&");
String result2 = tempResult[1];
String []result3 = result2.split("s_");
Now to get your desire number you just need to do
String finalResult = result3[1];
INPUT :
String s = "chapterId=c_1&sectionId=s_24666&isHL=1&cssFileName=haynes";
OUPUT :
24666

Checking whether the String contains multiple words

I am getting the names as String. How can I display in the following format: If it's single word, I need to display the first character alone. If it's two words, I need to display the first two characters of the word.
John : J
Peter: P
Mathew Rails : MR
Sergy Bein : SB
I cannot use an enum as I am not sure that the list would return the same values all the time. Though they said, it's never going to change.
String name = myString.split('');
topTitle = name[0].subString(0,1);
subTitle = name[1].subString(0,1);
String finalName = topTitle + finalName;
The above code fine, but its not working. I am not getting any exception either.
There are few mistakes in your attempted code.
String#split takes a String as regex.
Return value of String#split is an array of String.
so it should be:
String[] name = myString.split(" ");
or
String[] name = myString.split("\\s+);
You also need to check for # of elements in array first like this to avoid exception:
String topTitle, subTitle;
if (name.length == 2) {
topTitle = name[0].subString(0,1);
subTitle = name[1].subString(0,1);
}
else
topTitle = name.subString(0,1);
The String.split method split a string into an array of strings, based on your regular expression.
This should work:
String[] names = myString.split("\\s+");
String topTitle = names[0].subString(0,1);
String subTitle = names[1].subString(0,1);
String finalName = topTitle + finalName;
First: "name" should be an array.
String[] names = myString.split(" ");
Second: You should use an if function and the length variable to determine the length of a variable.
String initial = "";
if(names.length > 1){
initial = names[0].subString(0,1) + names[1].subString(0,1);
}else{
initial = names[0].subString(0,1);
}
Alternatively you could use a for loop
String initial = "";
for(int i = 0; i < names.length; i++){
initial += names[i].subString(0,1);
}
You were close..
String[] name = myString.split(" ");
String finalName = name[0].charAt(0)+""+(name.length==1?"":name[1].charAt(0));
(name.length==1?"":name[1].charAt(0)) is a ternary operator which would return empty string if length of name array is 1 else it would return 1st character
This will work for you
public static void getString(String str) throws IOException {
String[] strr=str.split(" ");
StringBuilder sb=new StringBuilder();
for(int i=0;i<strr.length;i++){
sb.append(strr[i].charAt(0));
}
System.out.println(sb);
}

Regex: extract float data from String and group it

i have a string like this one:
288.999,224.004 283.665,258.338 313.332,293.005 312.332,336.671 270.999,389.338 371.998,412.338
i try to parse the data to float values, but i want to sort it! The value before comma should by my x value and the value after comma should be the y value.
Pattern p = Pattern.compile("[0-9]+.[0-9]*");
Matcher m = p.matcher(pointString);
while(m.find())
{
System.out.print("x:"+m.group(0)); //x- Values
// System.out.print("y:"+m.group(1)); //y- Values
}
This code just creates a single group...How should i change my String pattern to get a second group with the y-Values...
favored result:
x:288.999
y:224.004
x:283.665
y:258.338
....
Keep it simple, split is enough:
String input = "288.999,224.004 283.665,258.338 313.332,293.005 312.332,336.671 270.999,389.338 371.998,412.338";
String[] points = input.split(" ");
for (String point : points) {
String[] coordinates = point.split(",");
System.out.println("x:" + coordinates[0]);
System.out.println("y:" + coordinates[1]);
}
The pattern you are looking for:
((?:\\d*\\.\\d+)|(?:\\d+\\.\\d*)) *, *((?:\\d*\\.\\d+)|(?:\\d+\\.\\d*))
also, group(0) would bring the whole match, you're rather looking for group(1) and group(2)
This will work
String str = "288.999,224.004 283.665,258.338 313.332,293.005 312.332,336.671 270.999,389.338 371.998,412.338";
String[] points=str.split(" ");
String[] point=new String[2];
for(int i=0;i<points.length;i++){
point=points[i].split(",");
System.out.println("X-val: "+point[0]);
System.out.println("Y-val: "+point[1]);
}

Java: slicing a String

I have URLs which always end on a number, for example:
String url = "localhost:8080/myproject/reader/add/1/";
String anotherurl = "localhost:8080/myproject/actor/take/154/";
I want to extract the number between the last two slashes ("/").
Does anyone know how I can do this?
You could split the string:
String[] items = url.split("/");
String number = items[items.length-1]; //last item before the last slash
With a regular expression:
final Matcher m = Pattern.compile("/([^/]+)/$").matcher(url);
if (m.find()) System.out.println(m.group(1));
Use lastIndexOf, like this:
String url = "localhost:8080/myproject/actor/take/154/";
int start = url.lastIndexOf('/', url.length()-2);
if (start != -1) {
String s = url.substring(start+1, url.length()-1);
int n = Integer.parseInt(s);
System.out.println(n);
}
That's the basic idea. You'll have to do some error checking (for example, if a number is not found at the end of the URL), but it will work fine.
For the inputs which you specified
String url = "localhost:8080/myproject/reader/add/1/";
String anotherurl = "localhost:8080/myproject/actor/take/154/";
adding a little error handling to handle missing "/" like
String url = "localhost:8080/myproject/reader/add/1";
String anotherurl = "localhost:8080/myproject/actor/take/154";
String number = "";
if(url.endsWith("/") {
String[] urlComps = url.split("/");
number = urlComps[urlComps.length-1]; //last item before the last slash
} else {
number = url.substring(url.lastIndexOf("/")+1, url.length());
}
In One Line :
String num = (num=url.substring(0, url.length() - 1)).substring(num.lastIndexOf('/')+1,num.length());

Splitting a period-delimited string into multiple strings

I have a string
String x = "Hello.August 27th.Links.page 1";
I am wondering if I can split this string into 4 other strings based on where the period is. For example, the four other strings would be,
String a = "Hello";
String b = "August 27th";
String c = "Links";
String d = "page 1";
As you can see I basically want to extract certain parts of the string out into a new string, the place where it is extracted is based on where the period is which ends the first string and then shows where the 2nd and, etc. strings end.
Thanks in advance!
In android btw
Use String#split (note that it receives a regex as a parameter)
String x = "Hello.August 27th.Links.page 1";
String[] splitted = x.split("\\.");
Yes of course just use:
String[] stringParts = myString.split("\\.")
String x = "Hello.August 27th.Links.page 1"
String []ar=x.split("[.]");
Perhaps you can use StringTokenizer for this requirement. Here is the simple approach:
String x = "Hello.August 27th.Links.page 1";
if (x.contains(".")) {
StringTokenizer stringTokenizer = new StringTokenizer(x, ".");
String[] arrayOfString = new String[stringTokenizer.countTokens()];
int i = 0;
while (stringTokenizer.hasMoreTokens()) {
arrayOfString[i] = stringTokenizer.nextToken();
i++;
}
System.out.println(arrayOfString[0]);
System.out.println(arrayOfString[1]);
System.out.println(arrayOfString[2]);
System.out.println(arrayOfString[3]);
}
You are done. :)

Categories

Resources