Static em métodos e a palavra chave 'super'

13 respostas
T
class SuperCalc
{
	protected static int multiply(int a, int b){ return a*b; }
}

public class SubCalc extends SuperCalc
{
	public static int multiply(int a, int b){
		int c = super.multiply(a,b);
		return c;
	}

	public static void main(String args[]){
		SubCalc sc = new SubCalc();

		System.out.println( sc.multiply(3,4) );
		System.out.println( SubCalc.multiply(2,2) );
	}
}

Por que não se pode usar a palavra chave "super" para chamar um método estático da superclasse? "super" só vale para chamar métodos de instância?

Obrigado!

13 Respostas

S

Quando um metodo ou atributo é statis significa que ele é pertencente a classe é a não há objetos partculares instanciados da classe dessa forma você pode chama-los pelos nome da classe veja:

NomeClasse.metodoStatico();

:wink:

V

Por que dois métodos estáticos na classe pai e na filha, mesmo que tenham o mesmo nome, são métodos diferentes. Em métodos estáticos, não existe sobrescrita, você acaba com dois métodos em escopos diferentes.

No seu exemplo, existe o método SuperCalc.multiply() e o SubCalc.multiply() e ambos podem ser usados a qualquer momento, por qualquer classe.

P

ViniGodoy se o método não é sobrescrito pq eu não posso alterar o modificador de acesso para um mais restritivo??
por ex:

class SuperCalc {

    public static int multiply(int a, int b) {
        return a * b;
    }
}

class SubCalc extends SuperCalc {

    protected static int multiply(int a, int b) {
        return a * b;
    }
    
}

ou

class SuperCalc {

    protected static int multiply(int a, int b) {
        return a * b;
    }
}

class SubCalc extends SuperCalc {

    static int multiply(int a, int b) {
        return a * b;
    }
}

não compila ;~
mesmo não sendo sobrescrito a regra de sobrescrição está sendo aplicada oO

V

Acho que isso vc teria que perguntar para o James Gosling. kkkk

Provavelmente por que você pode chamar um método estático de maneira não estática.
E nesse contexto, ele procurará chamar o método mais próximo.

Em todo caso, isso é considerado uma má prática de programação, e chamar métodos estáticos dessa forma não é recomendado desde o Java 1.1, mais ou menos.

T

Fiz outro teste aqui para ver se métodos estáticos "sobrecarregados" passam pela regra da exceção. Não passa!!!

Isso:

import java.io.*;

class SuperCalc {  
   
     static int multiply(int a, int b) throws IOException{  
         return a * b;  
     }  
}  
   
class SubCalc extends SuperCalc {  
   
     static int multiply(int a, int b) throws Exception{  
         return a * b;  
     }  
}

não compila!!! :shock:

Me parece que, apesar de não existir sobrescrita de métodos estáticos, todas as regras de sobreescrita são validas... :-o

Cada uma do Java... :lol:

A

Cara… essa foi uma das últimas questões de minha prova hoje… perdi ela por falta de paciência e porque já estava em OFF nessa hora, doido pra sair da sala da prova…

Falows :wink:

T
Outra bizarrice que encontrei. Vejam esses códigos:
class TestA{
	public void start(){ System.out.println("TestA"); }
}

public class TestB extends TestA{
	public static void start(){ System.out.println("TestB"); }
}
class TestA{
	public static void start(){ System.out.println("TestA"); }
}

public class TestB extends TestA{
	public void start(){ System.out.println("TestB"); }
}

Ambos não compilam! Agora, se alguém tiver alguma explicação...

P

Olá,

Nesse caso você esta tentando fazer uma sobrecarga de um método na subclasse e extende a classe TestA que contém um método static.

Acontece que métodos static não podem serem sobrescritos e muitos menos sobrecarregados.

Por exemplo na API Math seus métodos são static para que você acesse sem precisar de criar instâncias da classe Math.

Pois a classe Math alem de ser final não tem como instância-la.

P

e um métod static não pode sobrescrever um método não static e vice versa.

Essa é a regra

T

peresjuliao:
Olá,

Nesse caso você esta tentando fazer uma sobrecarga de um método na subclasse e extende a classe TestA …

Como assim? Eu não estou sobreescrevendo o método? :shock:

P
TiagoTC:
Ambos não compilam! Agora, se alguém tiver alguma explicação...
Como já foi dito atrás, métodos estáticos podem ser chamados de forma não estática. Assim, se tiveres:
class TestA{  
    public void start(){ System.out.println("TestA"); }  
}  
 
public class TestB extends TestA{  
    public static void start(){ System.out.println("TestB"); }  

    public static void main (String args[]){
        TestB b = new TestB();
        b.start(); // o que vai ser chamado aqui?
    }
}

Como é que ele sabe o que deve invocar na linha 10? O método estatico da própria classe (que pode ser chamado assim)? Ou o método da classe pai (seguindo a lógica do objecto)?

T
pmlm:
TiagoTC:
Ambos não compilam! Agora, se alguém tiver alguma explicação...
Como já foi dito atrás, métodos estáticos podem ser chamados de forma não estática. Assim, se tiveres:
class TestA{  
    public void start(){ System.out.println("TestA"); }  
}  
 
public class TestB extends TestA{  
    public static void start(){ System.out.println("TestB"); }  

    public static void main (String args[]){
        TestB b = new TestB();
        b.start(); // o que vai ser chamado aqui?
    }
}

Como é que ele sabe o que deve invocar na linha 10? O método estatico da própria classe (que pode ser chamado assim)? Ou o método da classe pai (seguindo a lógica do objecto)?

Esse código não compila.

P

Claro que não compila. É o teu código atrás com uma pequena alteração, onde tentei fazer ver porque não compila.

Criado 13 de janeiro de 2010
Ultima resposta 19 de jan. de 2010
Respostas 13
Participantes 7