The if statement in java is not working inside a method

6

I'm a beginner and I'm not getting my code to work as expected with the if / else.

I'm using this command within a method and doing it as follows:

private boolean AutentificaSenha(String s) {
    this.aSenha = s;
    boolean cond = this.senha == this.aSenha;
    if(cond) {
        return true;
    } else {
        return false; 
    }
}

My intention is to create a data authentication system to put into practice what I learned in some of the workbooks.

This method is one of 3 methods, after the 3 private methods there is a last public method that calls the other 3.

public boolean Autentifica() {     
    System.out.println("Seu nome: ");
    this.aNome = entrada.nextLine();
    System.out.println("Sua senha: ");
    this.aSenha = entrada.nextLine();   
    System.out.println("Seu ID: ");
    this.aId = entrada.nextInt();

    System.out.println("Aguarde");
    boolean cond =
        this.AutentificaNome(this.aNome) &&
        this.AutentificaSenha(this.senha) &&
        this.AutentificaId(this.id);
    if (cond) {
        System.out.println("Logado com sucesso");
        return true;
    } else{
        System.out.println("Falha ao efetuar loguin");
        return false;
    }
}

My problem is that when I run the code, it always appears "failed to log in" regardless of what I put in.

P.S. private variables: nome , senha and id are already defined.

    
asked by anonymous 04.07.2015 / 00:04

2 answers

8

You have not given the code for methods AutentificaNome and AutentificaId , but I will assume that they are analogous to AutentificaSenha .

So, I can rebuild your entire class more or less like this:

import java.util.Scanner;

public class TestaSenha {

    private Scanner entrada;
    private String senha;
    private String nome;
    private int id;
    private String aSenha;
    private String aNome;
    private int aId;

    public TestaSenha(Scanner entrada, String senha, String nome, int id) {
        this.entrada = entrada;
        this.senha = senha;
        this.nome = nome;
        this.id = id;
    }

    private boolean AutentificaNome(String s) {
        this.aNome = s;
        boolean cond = this.nome == this.aNome;
        if(cond) {
            return true;
        } else {
        return false; }
    }

    private boolean AutentificaSenha(String s) {
        this.aSenha = s;
        boolean cond = this.senha == this.aSenha;
        if(cond) {
            return true;
        } else {
        return false; }
    }

    private boolean AutentificaId(int s) {
        this.aId = s;
        boolean cond = this.id == this.aId;
        if(cond) {
            return true;
        } else {
        return false; }
    }

    public boolean Autentifica() {     
        System.out.println("Seu nome: ");
        this.aNome = entrada.nextLine();
        System.out.println("Sua senha: ");
        this.aSenha = entrada.nextLine();   
        System.out.println("Seu ID: ");
        this.aId = entrada.nextInt();

        System.out.println("Aguarde");
        boolean cond =
        this.AutentificaNome(this.aNome) &&
        this.AutentificaSenha(this.senha) &&
        this.AutentificaId(this.id);
        if (cond) {
            System.out.println("Logado com sucesso");
            return true;
        } else{
            System.out.println("Falha ao efetuar loguin");
            return false;
        }
    }
}

Your most serious mistake is that comparing String s using the == operator will not do what you want. You should use the equals() method. The reason is that == compares if two variables point to the same object, which will go wrong when you have two String s that although they have the same content, are two different objects. See more details in this question.

When doing str1.equals(str2) , true will be returned if both String s have the same content, and false otherwise, unless str1 is null , which will result in a% with%. In this case, we can use the following:

Objects.equals(str1, str2);

And do not forget to add% as required%:

import java.util.Objects;

So, here's how your code looks:

private boolean AutentificaSenha(String s) {
    this.aSenha = s;
    boolean cond = Objects.equals(this.senha, this.aSenha);
    if(cond) {
        return true;
    } else {
    return false; }
}

And the same goes for NullPointerException , but not for import (since AutentificaNome s are not objects, so it can compare with AutentificaId with no problem).

We can improve your code a little more, after all if the int is true, it will be returned true, and if == is false, it will be returned false. How about returning cond directly then?

private boolean AutentificaSenha(String s) {
    this.aSenha = s;
    boolean cond = Objects.equals(this.senha, this.aSenha);
    return cond;
}

We are returning cond , whose value is always the result of cond . So we can simplify it further by directly returning the result of cond :

private boolean AutentificaSenha(String s) {
    this.aSenha = s;
    return Objects.equals(this.senha, this.aSenha);
}

And Java naming rules dictate that method names should start with lowercase letters. So let's put all four of your methods with names starting with lowercase.

We can do something similar at the end of your main method too:

public boolean autentifica() {
    System.out.println("Seu nome: ");
    this.aNome = entrada.nextLine();
    System.out.println("Sua senha: ");
    this.aSenha = entrada.nextLine();   
    System.out.println("Seu ID: ");
    this.aId = entrada.nextInt();

    System.out.println("Aguarde");
    boolean cond =
            this.autentificaNome(this.aNome) &&
            this.autentificaSenha(this.senha) &&
            this.autentificaId(this.id);
    if (cond) {
        System.out.println("Logado com sucesso");
    } else {
        System.out.println("Falha ao efetuar login");
    }
    return cond;
}

Since we are looking at your main method, I have already used and typed the spelling of "loguin" to "login" and also gave a better idea of the Objects.equals(this.senha, this.aSenha) variable definition. Incidentally, let's analyze this variable better:

    boolean cond =
            this.autentificaNome(this.aNome) &&
            this.autentificaSenha(this.senha) &&
            this.autentificaId(this.id);
  • You read the variables Objects.equals(this.senha, this.aSenha) , cond and aNome of the user, but pass to the methods the variables aSenha , aId and aNome . Notice the inconsistency between the variables used.

  • In the senha method, the value of id will be assigned to the autentificaNome itself (which does nothing) and then compared to aNome .

    In the aNome method, the value of nome will be assigned to autentificaSenha , ignoring what the user typed and making the two passwords always equal.
  • With the senha method, something similar happens to aSenha .

Now we come to an important point, the autentificaId , autentificaSenha and aNome are important to remain recorded after the login test is performed? Assuming no, then ideally you would eliminate them and use only local variables to aSenha method. There is also no need to change the value of the object fields when you are just testing whether the password you entered is correct or not, after all a login attempt, whether successful or not, should not change the login and password, or something like this.

In this way, this is your code now:

import java.util.Scanner;
import java.util.Objects;

public class TestaSenha {

    private Scanner entrada;
    private String senha;
    private String nome;
    private int id;

    public TestaSenha(Scanner entrada, String senha, String nome, int id) {
        this.entrada = entrada;
        this.senha = senha;
        this.nome = nome;
        this.id = id;
    }

    private boolean autentificaNome(String s) {
        return Objects.equals(this.nome, s);
    }

    private boolean autentificaSenha(String s) {
        return Objects.equals(this.senha, s);
    }

    private boolean autentificaId(int s) {
        return this.id == s;
    }

    public boolean autentifica() {     
        System.out.println("Seu nome: ");
        String aNome = entrada.nextLine();
        System.out.println("Sua senha: ");
        String aSenha = entrada.nextLine();   
        System.out.println("Seu ID: ");
        int aId = entrada.nextInt();

        System.out.println("Aguarde");
        boolean cond =
                this.autentificaNome(aNome) &&
                this.autentificaSenha(aSenha) &&
                this.autentificaId(aId);
        if (cond) {
            System.out.println("Logado com sucesso");
        } else {
            System.out.println("Falha ao efetuar login");
        }
        return cond;
    }
}

Your class should already be working properly now. The only detail is that it is easier to encapsulate checking the three conditions together in a method of your own, so your code looks like this:

import java.util.Scanner;
import java.util.Objects;

public class TestaSenha {

    private Scanner entrada;
    private String senha;
    private String nome;
    private int id;

    public TestaSenha(Scanner entrada, String senha, String nome, int id) {
        this.entrada = entrada;
        this.senha = senha;
        this.nome = nome;
        this.id = id;
    }

    private boolean autentificaNome(String s) {
        return Objects.equals(this.nome, s);
    }

    private boolean autentificaSenha(String s) {
        return Objects.equals(this.senha, s);
    }

    private boolean autentificaId(int s) {
        return this.id == s;
    }

    private boolean autentifica(String n, String s, int i) {
        return this.autentificaNome(n) &&
               this.autentificaSenha(s) &&
               this.autentificaId(i);
    }

    public boolean autentifica() {     
        System.out.println("Seu nome: ");
        String aNome = entrada.nextLine();
        System.out.println("Sua senha: ");
        String aSenha = entrada.nextLine();   
        System.out.println("Seu ID: ");
        int aId = entrada.nextInt();

        System.out.println("Aguarde");
        boolean cond = this.autentifica(aNome, aSenha, aId);
        if (cond) {
            System.out.println("Logado com sucesso");
        } else {
            System.out.println("Falha ao efetuar login");
        }
        return cond;
    }
}
    
04.07.2015 / 01:12
4

Simple answer:

Strings in Java are objects and each has a different reference (memory address), for example this.senha and this.aSenha therefore testing the refences via operator == will always return false. In these cases always use the equals method.

boolean cond = this.senha != null && this.senha.equals(this.aSenha);

I'm assuming you want to make sure you've been informed of a password.

That's all!

    
04.07.2015 / 18:40