public void toonBoten()
{
for(Boot tweedeboot: boten)
{
Boot.toonBoot();
}
}
I'm trying to call the method toonBoot from the class Boot. This should be done for every tweedeboot of the type Boot (same as the class) from the ArrayList boten. toonBoot prints a few lines of information (basically it's a number of coordinates).
For some reason, I always receive the error "non-static method toonBoot() cannot be referenced from a static context".
What am I doing wrong?
Thanks!
You have to call method on instance.
public void toonBoten()
{
for(Boot tweedeboot: boten)
{
tweedeboot.toonBoot();
}
}
Where
Boot.toonBoot(); //means toonBoot() is a static method in Boot class
See:
Understanding Instance and Class Members
What you are doing
By calling the method from the Class name, you're telling the compiler that this method is a static method. That is, calling Boot.hello() that the method signature for hello() is something like:
public static void hello() {}
What you should do
Call from the object reference, or in this case tweedeboot. This tells the compiler that the method is either a static method or an instance method, and it will check the instance as well as the class.
Related
class Base {
public static void staticMethod(Base bObj) {
System.out.println("In Base.staticMethod()");
bObj.instanceMethod();
}
public void instanceMethod() {
System.out.println("In Base.instanceMethod()");
}
}
class Derived extends Base {
public static void staticMethod(Base bObj) {
System.out.println("In Derived.staticMethod()");
bObj.instanceMethod();
}
public void instanceMethod() {
System.out.println("In Derived.instanceMethod()");
}
}
public class Main {
public static void main(String []args) {
Base bObj = new Derived();
bObj.staticMethod(bObj);
}
}
Initially, when I saw this example I was sure that the result would be:
"In Base.staticMethod()"
"In Base.instanceMethod()".
After the initialization of the first Derived object it is obvious that it will be interpreted as a Base object due to upcast and it will call the static method of the base class which it does but later when it calls the other method(instance method) it goes inside the derived function instead of base class.
Why, considering that initially it was considered being Base?
There is no method overriding for static methods. Therefore bObj.staticMethod(), which is equivalent to Base.staticMethod, invokes the static method of the base class.
Inside the static method you are calling bObj.instanceMethod(). For instance methods there is method overriding, and the runtime type of bObj determines which method is executed - the instance method of Derived in your case.
Override is only for instance methods. For Static Method the term is called Method Hiding See Detail.
1. If method hiding is used then BaseClass's method is hidden from Subclass. method selection solely depends on which class's reference you are using to call the method. In your example since you are using BaseClass (even you assign Subclass object, it still on the class level it's BaseClass) reference to make a call to the static method it makes a call to BaseClass's method. If you would use SubClass reference as below then it would call the SubClass's static method
public static void main(String []) {
Derived bObj = new Derived();
bObj.staticMethod(bObj);
}
As the call inside the static method is for an Instance method. It uses polymorphism here and calls the SubClass's method.
TL;DR:
bObj.staticMethod(bObj); only looks at the compile-time type of bObj, and is equivalent to Base.staticMethod(bObj); in your case. There's no overriding.
bObj.instanceMethod(); only looks at the runtime class of bObj, and selects the method based on that class. So overriding works here.
Explanation
If you call a static method, you should do so by naming the class, not an instance. So bObj.staticMethod(bObj) should better be written Base.staticMethod(bObj). Typically, the compiler will issue a warning for the first version.
That's because the runtime instance is irrevant for selecting the static method. The decision is made by the compiler. And that's why we call this method type "static", because it lacks the dynamic method lookup of instance methods. That means that there is no overriding based on the instance "before the dot".
Using an instance expression misleads the reader into thinking the instance were relevant, and therefore should not be used. And inside the static method, there is no way to refer to the instance "before the dot". The keyword this doesn't exist in static methods. To call a static method, you don't even need an instance of that class (e.g. you can't create Math instances, but you can call Math.min() without any problem).
On the other hand, if you call an instance method, you need an instance of a class having that method, and this instance gets the name this inside the method. The method selection is done at runtime, based on the runtime class of the instance, no matter what the declared type is.
My code looks like this:
public abstract class BaseClass{
public void update() {
//...
}
public void somethingHappenedSoCallUpdate() {
update();
}
}
public class ExtendingClass extends BaseClass{
#Override
public void update() {
//...
}
}
There's an instance of ExtendingClass and at some point method somethingHappenedSoCallUpdate() is called. And I expect the method will call BaseClass.update() but ExtendingClass.update() is called. Can someone explain why?
And I expect the method will call BaseClass.update() but ExtendingClass.update() is called. Can someone explain why?
Because that's how Java is defined. By default, all non-private methods are virtual, which means that when you have overridden methods, the method that gets called on an instance is the instance's most-overridden version (ExtendingClass's, in your case), regardless of the type reference through which the method call is made. This is fundamental to polymorphism in modern OOP languages.
The compile-time type reference tells the compiler whether code has access to the method; the runtime type of the object tells the JVM which override of the method to call.
Let's take a simple example:
class Base {
public void method1() {
System.out.println("Base#method1");
}
}
class Derived extends Base {
#Override
public void method1() {
System.out.println("Derived#method1");
}
public void method2() {
System.out.println("Derived#method1");
}
}
// Usage:
Base b = new Derived();
b.method1(); // Calls Derived#method1, the most-overridden version the
// actual object has
b.method2(); // Fails to compile; Base doesn't define method2, so the
// code doesn't have access to call it when using a Base
// reference, even though the object does have the method
As #hyde said, Java methods are virtual, thats means that the VM decides at runtime which method to invoke. If you call somethingHappenedSoCallUpdate() on an instance that extends BaseClass then BaseClass.somethingHappenedSoCallUpdate() will be called, but since ExtendingClass is overriding BaseClass.update() it will class ExtendingClass.update() instead of BaseClass.update().
When extending a method you have to think of it like this:
whenever you extend a method you put it on a stack and when you invoke it, Java will look on this "stack" and invokes the topmost. That means if you have a BaseClass that has a update() method, this class can be extended by X classes not overriding the update() method but if the X+1 class does, Java will always call that method of X+1.
It's polymorphism:the right method is called at runtime depending on the real type of the object it's a dynamic binding.
Because you overrode update in subclass and since java methods are virtual overridden version is called.
Option #1
Override update, override somethingHappenedSoCallUpdate() method and use there super.update() instead of update().
Option #2
Make update private in superclass:
private void update()
You overrode the method so if you still want the code in the abstract class to run you need to implicitly call update() within the overridden method. So...
public class ExtendingClass extends BaseClass {
#Override
public void update() {
super.update(); // Call the base method.
}
}
Hope that helps :)
I'm beginner in Java and I have a basic question about main class and main method.I try to create method such as addition under the main method . throw the error like "non-static method". what is reason ? thanks...
I guess you using a code like this.
public class TestClass {
public static void main(String[] args) {
doSth();
}
public void doSth() {
}
You cannot call a non-static method from the main class.
If you want to call a non-static method from your main class, instance your class like this:
TestClass test = new TestClass();
test.doSth();
and call the method.
A static method means that you don't need to invoke the method on an instance(Object). A non-static (instance) method requires that you invoke it on an instance. So think about it: if I have a method changeThisItemToTheColorBlue() and I try to run it from the main method, what instance would it change? It doesn't know. You can run an instance method on an instance, like someItem.changeThisItemToTheColorBlue().
More information at http://en.wikipedia.org/wiki/Method_(computer_programming)#Static_methods
The only way to call a non-static method from a static method is to have an instance of the class containing the non-static method. By definition, a non-static method is one that is called ON an instance of some class, whereas a static method belongs to the class itself.
Is like when you try to invoke the non-static method startsWith of class String without an instance:
String.startsWith("Hello");
What you need is to have an instance and then invoke the non-static method:
String greeting = new String("Hello World");
greeting.startsWith("Hello"); // returns true
So you need to create and instance to invoke it.
And to be more clear about Static methods you can refer
https://softwareengineering.stackexchange.com/questions/211137/why-can-static-methods-only-use-static-data
You defined your method without the keyword 'static' I think.
You cannot call a non-static method in a static context such as the main method.
See Java Object Oriented Programming
The main method is a static method, so it does not exist inside an object.
To call non-static methods (methods without the "static" keyword in front of their definitions), you need to create an object of the class, using new.
You can just make the other method static, that will fix the immediate problem. But it may or may not be good Object Oriented design to do this. It would depend on what you were trying to do.
You can't call a non-static method from a static method without instantiation of the class. If you'd like to call another method without creating a new instance (a new object) of the main class you have to use the static keyword for the another method also.
package maintestjava;
public class Test {
// static main method - this is the entry point
public static void main(String[] args)
{
System.out.println(Test.addition(10, 10));
}
// static method - can be called without instantiation
public static int addition(int i, int j)
{
return i + j;
}
}
If you would like to call non static methods you have to instatiate the class, this way creating a new instance, an object of the class:
package maintestjava;
public class Test {
// static main method - this is the entry point
public static void main(String[] args)
{
Test instance = new Test();
System.out.println(instance.addition(10, 10));
}
// public method - can be called with instantiation on a created object
public int addition(int i, int j)
{
return i + j;
}
}
See more:
Static keyword on wikipedia
Static on about.com
I came across this scenario. We have a class lets say Main having a private method print. There is another class Main1 which extends Main class and redefines the print method. Since main1 is an object of Main1 class, I expect main1 print method to get called...
public class Main {
public static void main(String[] args) {
Main main1 = new Main1();
List<String> list = new ArrayList<String>();
main1.print(list);
}
private void print(List<String> string) {
System.out.println("main");
}
}
class Main1 extends Main {
public void print(List<String> string) {
System.out.println("main1");
}
}
In this case, when we run the program, it print "main". It really confuses me as that method is private and is not even part of Main1 class.
The answer is not too hard:
the type of the main1 variable is Main (not Main1)
so you can only call methods of that type
the only possible method called print that accepts a List<String> on Main is the private one
the calling code is inside the class Main so it can call a private method in that class
Therefore Main.print(List<String>) will be called.
Note that changing the type of main1 to Main1 will result in the other print(List<String>) method being called.
If you want to be able to override your print method you have to declare it public:
public class Main {
public void print(List<String> string) {
}
}
Otherwise it will call your private method without looking for the implementation in a derived class .
Private method is not inherited and method overriding does not happened in your code.
You can see this by putting #Override annotation in Main1.print() method. If you put that annotation, compile error generated.
Main.java:17: method does not override or implement a method from a supertype
#Override
^
1 error
In your case, Main1.print() and Main.print() are different and not related each other(no overriding, no overloading). So if you specify main1 as Main, Main.print() will be called. And if you specify main1 as Main1, Main1.print() will be called.
Your main1 is a type of Main but instantiated with as Main1! It's OK since it is a subclass for Main. However, when you call the print method (BTW, it should be main1.print(list);) it will call the private method in the Main class! If you change the visibility of your method to protected or public, in this case print method in the Main1 class will be called because of polymorphic behavior of your instantiated object (remember, it is after all a Main1 object based on the code that you've provided!)
This question already has answers here:
Cannot make a static reference to the non-static method
(8 answers)
Closed 5 years ago.
I'm getting an error when I try to call a non-static method in a static class.
Cannot make a static reference to the non-static method methodName() from the type playback
I can't make the method static as this gives me an error too.
This static method cannot hide the instance method from xInterface
Is there any way to get round calling an non-static method in another static method? (The two methods are in seperate packages and seperate classes).
The only way to call a non-static method from a static method is to have an instance of the class containing the non-static method. By definition, a non-static method is one that is called ON an instance of some class, whereas a static method belongs to the class itself.
You could create an instance of the class you want to call the method on, e.g.
new Foo().nonStaticMethod();
Firstly create a class Instance and call the non-static method using that instance.
e.g,
class demo {
public static void main(String args[]) {
demo d = new demo();
d.add(10,20); // to call the non-static method
}
public void add(int x ,int y) {
int a = x;
int b = y;
int c = a + b;
System.out.println("addition" + c);
}
}
public class StaticMethod{
public static void main(String []args)throws Exception{
methodOne();
}
public int methodOne(){
System.out.println("we are in first methodOne");
return 1;
}
}
the above code not executed because static method must have that class reference.
public class StaticMethod{
public static void main(String []args)throws Exception{
StaticMethod sm=new StaticMethod();
sm.methodOne();
}
public int methodOne(){
System.out.println("we are in first methodOne");
return 1;
}
}
This will be definitely get executed. Because here we are creating reference which nothing but "sm" by using that reference of that class which is nothing
but (StaticMethod=new Static method()) we are calling method one (sm.methodOne()).
I hope this will be helpful.
You need an instance of the class containing the non static method.
Is like when you try to invoke the non-static method startsWith of class String without an instance:
String.startsWith("Hello");
What you need is to have an instance and then invoke the non-static method:
String greeting = new String("Hello World");
greeting.startsWith("Hello"); // returns true
So you need to create and instance to invoke it.
It sounds like the method really should be static (i.e. it doesn't access any data members and it doesn't need an instance to be invoked on). Since you used the term "static class", I understand that the whole class is probably dedicated to utility-like methods that could be static.
However, Java doesn't allow the implementation of an interface-defined method to be static. So when you (naturally) try to make the method static, you get the "cannot-hide-the-instance-method" error. (The Java Language Specification mentions this in section 9.4: "Note that a method declared in an interface must not be declared static, or a compile-time error occurs, because static methods cannot be abstract.")
So as long as the method is present in xInterface, and your class implements xInterface, you won't be able to make the method static.
If you can't change the interface (or don't want to), there are several things you can do:
Make the class a singleton: make the constructor private, and have a static data member in the class to hold the only existing instance. This way you'll be invoking the method on an instance, but at least you won't be creating new instances each time you need to call the method.
Implement 2 methods in your class: an instance method (as defined in xInterface), and a static method. The instance method will consist of a single line that delegates to the static method.
The only way to call a non-static method from a static method is to have an instance of the class containing the non-static method.
class A
{
void method()
{
}
}
class Demo
{
static void method2()
{
A a=new A();
a.method();
}
/*
void method3()
{
A a=new A();
a.method();
}
*/
public static void main(String args[])
{
A a=new A();
/*an instance of the class is created to access non-static method from a static method */
a.method();
method2();
/*method3();it will show error non-static method can not be accessed from a static method*/
}
}
There are two ways:
Call the non-static method from an instance within the static method. See fabien's answer for an oneliner sample... although I would strongly recommend against it. With his example he creates an instance of the class and only uses it for one method, only to have it dispose of it later. I don't recommend it because it treats an instance like a static function.
Change the static method to a non-static.
You can't get around this restriction directly, no. But there may be some reasonable things you can do in your particular case.
For example, you could just "new up" an instance of your class in the static method, then call the non-static method.
But you might get even better suggestions if you post your class(es) -- or a slimmed-down version of them.
The easiest way to use a non-static method/field within a a static method or vice versa is...
(To work this there must be at least one instance of this class)
This type of situation is very common in android app development eg:- An Activity has at-least one instance.
public class ParentClass{
private static ParentClass mParentInstance = null;
ParentClass(){
mParentInstance = ParentClass.this;
}
void instanceMethod1(){
}
static void staticMethod1(){
mParentInstance.instanceMethod1();
}
public static class InnerClass{
void innerClassMethod1(){
mParentInstance.staticMethod1();
mParentInstance.instanceMethod1();
}
}
}
Note:- This cannot be used as a builder method like this one.....
String.valueOf(100);
I use an interface and create an anonymous instance of it like so:
AppEntryPoint.java
public interface AppEntryPoint
{
public void entryMethod();
}
Main.java
public class Main
{
public static AppEntryPoint entryPoint;
public static void main(String[] args)
{
entryPoint = new AppEntryPoint()
{
//You now have an environment to run your app from
#Override
public void entryMethod()
{
//Do something...
System.out.println("Hello World!");
}
}
entryPoint.entryMethod();
}
public static AppEntryPoint getApplicationEntryPoint()
{
return entryPoint;
}
}
Not as elegant as creating an instance of that class and calling its own method, but accomplishes the same thing, essentially. Just another way to do it.
It is not possible to call non-static method within static method. The logic behind it is we do not create an object to instantiate static method, but we must create an object to instantiate non-static method. So non-static method will not get object for its instantiation inside static method, thus making it incapable for being instantiated.
Constructor is a special method which in theory is the "only" non-static method called by any static method. else its not allowed.
You can call a non static method within a static one using:
Classname.class.method()