Struggling with substring() logic for 2 character string on CodingBat

Viewed 366

I've worked through it several times, but I can't figure out how CodingBat's solution code correctly returns a two character string.

This is their solution:

 public String frontBack(String str) {
 if (str.length() <= 1) return str;
 
 String mid = str.substring(1, str.length()-1);
 
 // last + mid + first
 return str.charAt(str.length()-1) + mid + str.charAt(0);
 }

But why does this work for two character strings? If str = "AB" shouldn't the code return "B" (first part of return) + "B" (in this case wouldn't mid="B") and "A"...so "BBA"? I think I'm missing some logic with how String mid is created with a 2 character string. Thanks!

5 Answers

It is easier to work with substring method if you think that letters are between indexes like shown below for "AB"

 A B
^ ^ ^
0 1 2

and substring(a,b) would return characters placed between index a and b.

So when we execute code like:

  • "AB".substring(0,2) we get full "AB",
  • "AB".substring(0,1) we get "A"

What seems to be confusing you is part when we execute code like: "AB".substring(1,1) OR (0,0) OR (2,2).
When we use same value for start and end index, then result of substring will be empty string "" because there are no characters between those indexes.

Lets go back to your example.

When str = "AB" and we execute

String mid = str.substring(1, str.length()-1);

then it is same as executing substring(1, 2-1) => substring(1,1) which means mid will be holding empty string "".

Now when we call

return str.charAt(str.length()-1) + mid + str.charAt(0);

it will be evaluated as

return 'B' + "" + 'A';

which means we will end up with

return "BA";

I recommend installing Eclipse or Other IDE and run the example in Debug. It's one of the best ways to learn JAVA. From your example I can tell you the following: Mid will be null because is making a substring from position 1 to 1 => the length = 0

For str = "AB" Debug capture: enter image description here

If the substring was from 1 to 2 then it would had showed letter B: enter image description here

So you will only see as result str.charAt(str.length()-1) + str.charAt(0) Which is B and A.

The code swaps the first and last characters of a string. For a string of length 2, it stores nothing in mid because str.substring(1,1) returns an empty string. Then it returns the concatenation of the last character, the empty string stored in mid and the first character.

public class MyClass {
    public static void main(String args[]) {
       String str = "AB";
       if (str.length() <= 1) System.out.println(str);
       String mid = str.substring(1, str.length()-1);
       System.out.println("mid: "+mid);
       System.out.println("last: "+str.charAt(str.length()-1));
       // last + mid + first
      System.out.println(str.charAt(str.length()-1) + mid + str.charAt(0));
    }
}

This prints an empty line, then B, then BA.

The parameters for substring() is inclusive/exclusive so when the indices are the same, substring() will return an empty string. With a 2 length string, this means the mid value is empty.

Here's a walkthrough of the code with "AB" as the input

public String frontBack(String str) { // str = "AB"
// str.length() = 2, so continue
if (str.length() <= 1) return str;    

// str.length()-1 = 1, so str.substring(1,1) which is empty string.
// mid = "";
String mid = str.substring(1, str.length()-1);

// last + mid + first

// str.charAt(str.length()-1) = "B"
// str.charAt(0) = "A"
// "B" + "" + "A" = "BA"
return str.charAt(str.length()-1) + mid + str.charAt(0);

// returns "BA"
}
public static String frontBack(String str) {
    if (str.length() < 2)
        return str;

    char first = str.charAt(0);
    char last = str.charAt(str.length() - 1);

    if (str.length() == 2)
        return Character.toString(last) + first;
    return last + str.substring(1, str.length() - 1) + first;
}
Related