Java String split returns length 0 - java

public int lengthOfLastWord(String s) {
s.replaceAll("\\s", "");
String[] splittedS = s.split("\\s+");
if(splittedS.length == 1 && splittedS[0].equals("")) return 0;
return splittedS[splittedS.length - 1].length();
}
I tested it out with the string " ", and it returns that the length of splittedS is 0.
When I trimmed the String did I get " " -> "", so when I split this, I should have an array of length with with the first element being ""?

Java Strings are immutable so you have to store the reference to the returned String after replacement because a new String has been returned. You have written,
s.replaceAll("\\s", "");
But write,
s = s.replaceAll("\\s", "");
instead of above.
Wherever you perform operations on String, keep the new reference moving further.

The call to replaceAll has no effect, but since you split on \\s+, split method works exactly the same: you end up with an empty array.
Recall that one-argument split is the same as two-argument split with zero passed for the second parameter:
String[] splittedS = s.split("\\s+", 0);
// ^^^
This means that regex pattern is applied until there's no more changes, and then trailing empty strings are removed from the array.
This last point is what makes your array empty: the application of \\s+ pattern produces an array [ "" ], with a single empty string. This string is considered trailing by split, so it is removed from the result.
This result is not going to change even if you fix the call to replaceAll the way that other answers suggest.

You need to re assign the variable
s=s.replaceAll(...)

Related

Java - Why does string split for empty string give me a non empty array?

I want to split a String by a space. When I use an empty string, I expect to get an array of zero strings. Instead, I get an array with only empty string. Why ?
public static void main(String [] args){
String x = "";
String [] xs = x.split(" ");
System.out.println("strings :" + xs.length);//prints 1 instead of 0.
}
The single element string array entry is in fact empty string. This makes sense, because the split on " " fails, and hence you just get back the input with which you started. As a general approach, you may consider that if splitting returns you a single element, then the split did not match anything, leaving you with the starting input string.
An interesting puzzle indeed:
> "".split(" ")
String[1] { "" }
> " ".split(" ")
String[0] { }
The question is, when you split the empty string, why does the result contain the empty string, and when you split a space, why does the result not contain anything? It seems inconsistent, but all is explained in the documentation.
The String.split(String) method "works as if by invoking the two-argument split method with the given expression and a limit argument of zero", so let's read the docs for String.split(String, int). The case of the empty string is answered by this part:
If the expression does not match any part of the input then the resulting array has just one element, namely this string.
The empty string has no part matching a space, so the output is an array containing one element, the input string, exactly as the docs say should happen.
The case of the string " " is answered by these two parts:
A zero-width match at the beginning however never produces such empty leading substring.
If n is zero then the pattern will be applied as many times as possible, the array can have any length, and trailing empty strings will be discarded.
The whole input string " " matches the splitting pattern. In principle we could include an empty string on either side of the match, but the docs say that an empty leading substring is never included, and (because the limit parameter n = 0) the trailing empty string is also discarded. Hence, the empty strings before and after the match are both not included in the resulting array, so it's empty.
It appears that since the String exists and it cannot be split (there are no spaces), it simply places the entire String into the first array position, causing there to be one. If you were to instead try
String x = " ";
String [] xs = x.split(" ");
System.out.println("strings :" + xs.length);//prints 1 instead of 0.
It will give you the zero you are expecting.
See also: Java String split removed empty values

String.split(String pattern) Java method is not working as intended

I'm using String.split() to divide some Strings as IPs but its returning an empty array, so I fixed my problem using String.substring(), but I'm wondering why is not working as intended, my code is:
// filtrarIPs("196.168.0.1 127.0.0.1 255.23.44.1 100.168.100.1 90.168.0.1","168");
public static String filtrarIPs(String ips, String filtro) {
String resultado = "";
String[] lista = ips.split(" ");
for (int c = 0; c < lista.length; c++) {
String[] ipCorta = lista[c].split("."); // Returns an empty array
if (ipCorta[1].compareTo(filtro) == 0) {
resultado += lista[c] + " ";
}
}
return resultado.trim();
}
It should return an String[] as {"196"."168"."0"."1"}....
split works with regular expressions. '.' in regular expression notation is a single character. To use split to split on an actual dot you must escape it like this: split("\\.").
Use
String[] ipCorta = lista[c].split("\\.");
in regular expressions the . matches almost any character.
If you want to match the dot you have to escape it \\..
Your statement
lista[c].split(".")
will split the first String "196.168.0.1" by any (.) character, because String.split takes a regular expression as argument.
However, the point, why you are getting an empty array is, that split will also remove all trailing empty Strings in the result.
For example, consider the following statement:
String[] tiles = "aaa".split("a");
This will split the String into three empty values like [ , , ]. Because of the fact, that the trailing empty values will be removed, the array will remain empty [].
If you have the following statement:
String[] tiles = "aaab".split("a");
it will split the String into three empty values and one filled value b like [ , , , "b"]
Since there are no trailing empty values, the result remains with these four values.
To get rid of the fact, that you don't want to split on every character, you have to escape the regular expression like this:
lista[c].split("\\.")
String.split() takes a regular expression as parameter, so you have to escape the period (which matches on anything). So use split("\\.") instead.
THis may help you:
public static void main(String[] args){
String ips = "196.168.0.1 127.0.0.1 255.23.44.1 100.168.100.1 90.168.0.1";
String[] lista = ips.split(" ");
for(String s: lista){
for(String s2: s.split("\\."))
System.out.println(s2);
}
}

having trouble with arrays and maybe split

String realstring = "&&&.&&&&";
Double value = 555.55555;
String[] arraystring = realstring.split(".");
String stringvalue = String.valueof(value);
String [] valuearrayed = stringvalue.split(".");
System.out.println(arraystring[0]);
Sorry if it looks bad. Rewrote on my phone. I keep getting ArrayIndexOutOfBoundsException: 0 at the System.out.println. I have looked and can't figure it out. Thanks for the help.
split() takes a regexp as argument, not a literal string. You have to escape the dot:
string.split("\\.");
or
string.split(Pattern.quote("."));
Or you could also simply use indexOf('.') and substring() to get the two parts of your string.
And if the goal is to get the integer part of a double, you could also simply use
long truncated = (long) doubleValue;
split uses regex as parameter and in regex . means "any character except line separators", so you could expect that "a.bc".split(".") would create array of empty strings like ["","","","",""]. Only reason it is not happening is because (from split javadoc)
This method works as if by invoking the two-argument split method with the given expression and a limit argument of zero. Trailing empty strings are therefore not included in the resulting array.
so because all strings are empty you get empty array (and that is because you see ArrayIndexOutOfBoundsException).
To turn off removal mechanism you would have to use split(regex, limit) version with negative limit.
To split on . literal you need to escape it with \. (which in Java needs to be written as "\\." because \ is also Strings metacharacter) or [.] or other regex mechanism.
Dot (.) is a special character so you need to escape it.
String realstring = "&&&.&&&&";
String[] partsOfString = realstring.split("\\.");
String part1 = partsOfString[0];
String part2 = partsOfString[1];
System.out.println(part1);
this will print expected result of
&&&
Its also handy to test if given string contains this character. You can do this by doing :
if (string.contains(".")) {
// Split it.
} else {
throw new IllegalArgumentException("String " + string + " does not contain .");
}

Not sure how string split actually works in this case

I don't get the following:
In the following String:
String s = "1234;x;;y;";
if I do:
String[] s2 = s.split(";");
I get s2.length to be 4 and
s2[0] = "1234";
s2[1] = "x";
s2[2] = "";
s2[3] = "y";
But in the string: String s = "1234;x;y;;";
I get:
s2.length to be 3 and
s2[0] = "1234";
s2[1] = "x";
s2[2] = "y";
?
What is the difference and I don't get 4 in the latter case as well?
UPDATE:
Using -1 is not was I was expecting as behavior.
I mean the last semicolon is the end of the String so in the latter example I was also expecting 4 as length of the array
From the docs,
This method works as if by invoking the two-argument split method with
the given expression and a limit argument of zero. Trailing empty
strings are therefore not included in the resulting array.
UPDATE:
You have five substrings separated by ; In the second case, these are 1234, x, y, and . As per the docs, all empty substrings (at the end) which result from the split operation would be eliminated.
For details, look here.
If n is zero then the pattern will be applied as many times as
possible, the array can have any length, and trailing empty strings
will be discarded.
The string boo:and:foo, for example, yields the following results with these parameters:
Regex Limit Result
: 2 { "boo", "and:foo" }
: 5 { "boo", "and", "foo" }
: -2 { "boo", "and", "foo" }
o 5 { "b", "", ":and:f", "", "" }
o -2 { "b", "", ":and:f", "", "" }
o 0 { "b", "", ":and:f" } // all the empty substrings at the end were eliminated
Trailing empty strings are omitted. However, there are ways to include them explicitly, if needed.
From http://docs.oracle.com/javase/6/docs/api/java/lang/String.html#split(java.lang.String)
This method works as if by invoking the two-argument split method with the given expression and a limit argument of zero. Trailing empty strings are therefore not included in the resulting array.
Good question. If you check the API documentation for String.split() and check the example with "boo:foo" then you can see that the trailing empty strings are omitted.
This method works as if by invoking the two-argument split method with the given expression and a limit argument of zero. Trailing empty strings are therefore not included in the resulting array.
The string "boo:and:foo", for example, yields the following results with these expressions:
Regex Result
: { "boo", "and", "foo" }
o { "b", "", ":and:f" }
Thats default behavior of split method in java to not return empty tokens . ]
s.split("\;", -1); should return empty token
Why not check what does the documention says first. Here is the link:
http://docs.oracle.com/javase/6/docs/api/java/lang/String.html#split%28java.lang.String%29
And here is your answer:
Trailing empty strings are therefore not included in the resulting
array.

How can split a string which contains only delimiter?

I am using the following code:
String sample = "::";
String[] splitTime = sample.split(":");
// extra detail omitted
System.out.println("Value 1 :"+splitTime[0]);
System.out.println("Value 2 :"+splitTime[1]);
System.out.println("Value 3 :"+splitTime[2]);
I am getting ArrayIndexOutofBound exception. How does String.split() handle consecutive or trailing / opening delimiters?
See also:
Doubt in split method
Java split() method strips empty strings at the end?
Alnitak is correct that trailing empty strings will be discarded by default.
If you want to have trailing empty strings, you should use split(String, int) and pass a negative number as the limit parameter.
The limit parameter controls the number of times the
pattern is applied and therefore affects the length of the resulting
array. If the limit n is greater than zero then the pattern
will be applied at most n - 1 times, the array's
length will be no greater than n, and the array's last entry
will contain all input beyond the last matched delimiter. If n
is non-positive then the pattern will be applied as many times as
possible and the array can have any length. If n is zero then
the pattern will be applied as many times as possible, the array can
have any length, and trailing empty strings will be discarded.
Note that split(aString) is a synonym for split(aString, 0):
This method works as if by invoking the two-argument split method with the given expression and a limit argument of zero. Trailing empty strings are therefore not included in the resulting array.
Also, you should use a loop to get the values from the array; this avoids a possible ArrayIndexOutOfBoundsException.
So your corrected code should be (assuming you want the trailing empty strings):
String sample = "::";
String[] splitTime = sample.split(":", -1);
for (int i = 0; i < splitTime.length; i++) {
System.out.println("Value " + i + " : \"" + splitTime[i] + "\"");
}
Output:
Value 0 : ""
Value 1 : ""
Value 2 : ""
From the J2SE API manual:
Trailing empty strings are therefore not included in the resulting array.
So, if you pass in "::" you'll get an empty array because all of the delimiters are trailing.
If you want to make sure that you get no more than three entries you should use:
String[] splitTime = sample.split(":", 3);
With an input of "::" that would indeed give you three empty strings in the output array.
However if the input only happens to have one ":" in it then you'll still only get two elements in your array.
Like this perhaps?
int ndx = 0;
StringTokenizer t = new StringTokenizer(": : ::::",":");
while (t.hasMoreElements())
{
System.out.println(String.format("Value %d : %s", ++ndx,t.nextElement()));
}
you should check the length of the splitTime array.
Use the function StringTokenizer in which u pass the string and the second argument as delimiter
use splittime.length function to find the length

Categories