substring(int) method magically doesn't throw StringIndexOutOfBoundsException [duplicate]

Why does "a".substring(1) not throw StringIndexOutOfBoundsException, while it does for index that is >= 2? It is really interesting.


you will get answer in source code :

 public String substring(int beginIndex) {
        if (beginIndex < 0) {
            throw new StringIndexOutOfBoundsException(beginIndex);
        }
        int subLen = value.length - beginIndex;
        if (subLen < 0) {
            throw new StringIndexOutOfBoundsException(subLen);
        }
        return (beginIndex == 0) ? this : new String(value, beginIndex, subLen);
    }

where value.length will get 1 in your condition so

int subLen = value.length - beginIndex; 

which will become like :

int subLen = 1 - 1;

and subLen will be 0 so if (subLen < 0) { will be false and it wont throw exception :)


Behaves as specified in the JavaDoc.

Throws: IndexOutOfBoundsException - if beginIndex is negative or larger than the length of this String object.

Also, from the examples in the JavaDoc:

"emptiness".substring(9) returns "" (an empty string)

Therefore, "a".substring(1) returns an empty string, as it should.


Because you get an empty string back i.e, "".

public static void main(String[] args) {
System.out.println("a".substring(1).equals("")); // substring --> from index 1 upto length of "a" (which is also 1)

}

O/P :

true

You get StringIndexOutOfBoundsException when the int argument is greater that length of the String.

example :

System.out.println("a".substring(2).equals("")); // throws StringIndexOutOfBoundsException


a.substring(1) returns an empty string which is why it does not throw an exception as explained in this question. String.substring(n) only fails if n is greater than the length of the string.


Take a look at what substring() does.

 public String substring(int beginIndex) {
    if (beginIndex < 0) {
        throw new StringIndexOutOfBoundsException(beginIndex);
    }
    int subLen = value.length - beginIndex;
    if (subLen < 0) {
        throw new StringIndexOutOfBoundsException(subLen);
    }
    return (beginIndex == 0) ? this : new String(value, beginIndex, subLen);
}

int subLen = value.length - beginIndex; if subLen<0 exception will throw. In your case that won't happen.

In your case value.length=1 and beginIndex=1 then 1-1=0