1

I am trying to understand the output of the below Java code:

public class BasePage
{

    private final StringBuilder str;

    public BasePage(StringBuilder str)
    {
        this.str = str;
    }

    protected StringBuilder getStr()
    {
        return str;
    }
}

public class HomePage extends BasePage
{
    public HomePage(StringBuilder str)
    {
        super(str);     
    }
    
    public void navigateTo()
    {
        getStr().append("Sawant");
    }
}

public class LoginPage extends BasePage
{

    public LoginPage(StringBuilder str)
    {
        super(str); 
    }

}

public class LoginPage extends BasePage
{

    public LoginPage(StringBuilder str)
    {
        super(str); 
    }

    public HomePage login()
    {
        
        HomePage homePage = new HomePage(getStr());
        
        System.out.println("LoginPage value of str: " + getStr());
        System.out.println("HomePage value of str: " + homePage.getStr());
        if(getStr().toString().equals(homePage.getStr().toString()))
            System.out.println("Equals");
        else
            System.out.println("Not Equal");
        
        homePage.navigateTo();

        System.out.println("LoginPage value of str: " + getStr());
        System.out.println("HomePage value of str: " + homePage.getStr());
        if(getStr().toString().equals(homePage.getStr().toString()))
            System.out.println("Equals");
        else
            System.out.println("Not Equal");
        
        return new HomePage(getStr());
        
    }
    
}

public class TestClass
{
    private StringBuilder str = new StringBuilder("Sandesh");

    public static void main(String[] args)
    {

        LoginPage loginPage = new LoginPage(new TestClass().str);
        loginPage.login();
        
    }

}

Output of the above code:

LoginPage value of str: Sandesh
HomePage value of str: Sandesh
Equals
LoginPage value of str: SandeshSawant
HomePage value of str: SandeshSawant
Equals

As per my understanding, each object of the subclass maintains it's own value of the private instance variable belonging to it's superclass. Then why did the value of str of loginPage object changed to "SandeshSawant" when I changed only the value of str of homePage object by calling the navigateTo method of the HomePageClass.

But if move the entire code of the login method to the TestClass main method, then the str value of the loginPage object did not change.

Appreciated your help on improving my understanding on this.

1 Answers1

2

You're carrying around the same reference of a StringBuilder which all modify the same string buffer.

Try returning the actual string instance

protected String getStr()
{
    return str.toString();
}

And change navigate method to use the field directly

public void navigateTo()
{
    super.str.append("Sawant");
}
OneCricketeer
  • 179,855
  • 19
  • 132
  • 245
  • Thanks for the explaination. But my question is even if I use StringBuilder class and if I move the entire code of the login method to the TestClass, then the str value of the loginPage object did not change. I want to know why ? – Sandesh Sawant Mar 08 '22 at 17:51
  • What do you mean "entire code"? If you create `new StringBuilder()` inside the test method, and never pass it as a parameter to other places, then there is still only one reference to it. Sounds like you are not "moving code" correctly – OneCricketeer Mar 08 '22 at 18:21