Can you write virtual functions / methods in Java?
Asked Answered
C

6

194

Is it possible to write virtual methods in Java, as one would do in C++?

Or, is there a proper Java approach which you can implement that produces similar behavior? Could I please have some examples?

Corkboard answered 28/12, 2010 at 16:17 Comment(0)
T
352

From wikipedia

In Java, all non-static methods are by default "virtual functions." Only methods marked with the keyword final, which cannot be overridden, along with private methods, which are not inherited, are non-virtual.

Thriftless answered 28/12, 2010 at 16:19 Comment(5)
Here is one of Jon Skeet's answer.Ribosome
I wonded if it's really true, because for what I've read, in Java, dynamic method dispatch happens only for the object the method is called on - as explained here so the example explaining virtual functions for C++ here is not valid for java.Sori
@QuaziIrfan That is difference between Java and C# though.Kial
A final method in Java still can be virtual. For example, we have a Base class with some method, and Derived class that extends Base and has its own implementation of some method marked by final reserved word. The some method is still virtual.Oaf
@Oaf No, you cant override a final method. You will get a compiler error.Lambrequin
D
110

Can you write virtual functions in Java?

Yes. In fact, all instance methods in Java are virtual by default. Only certain methods are not virtual:

  • Class methods (because typically each instance holds information like a pointer to a vtable about its specific methods, but no instance is available here).
  • Private instance methods (because no other class can access the method, the calling instance has always the type of the defining class itself and is therefore unambiguously known at compile time).

Here are some examples:

"Normal" virtual functions

The following example is from an old version of the wikipedia page mentioned in another answer.

import java.util.*;

public class Animal 
{
   public void eat() 
   { 
      System.out.println("I eat like a generic Animal."); 
   }

   public static void main(String[] args) 
   {
      List<Animal> animals = new LinkedList<Animal>();

      animals.add(new Animal());
      animals.add(new Fish());
      animals.add(new Goldfish());
      animals.add(new OtherAnimal());

      for (Animal currentAnimal : animals) 
      {
         currentAnimal.eat();
      }
   }
}

class Fish extends Animal 
{
   @Override
   public void eat() 
   { 
      System.out.println("I eat like a fish!"); 
   }
}

class Goldfish extends Fish 
{
   @Override
   public void eat() 
   { 
      System.out.println("I eat like a goldfish!"); 
   }
}

class OtherAnimal extends Animal {}

Output:

I eat like a generic Animal.
I eat like a fish!
I eat like a goldfish!
I eat like a generic Animal.

Example with virtual functions with interfaces

Java interface methods are all virtual. They must be virtual because they rely on the implementing classes to provide the method implementations. The code to execute will only be selected at run time.

For example:

interface Bicycle {         //the function applyBrakes() is virtual because
    void applyBrakes();     //functions in interfaces are designed to be 
}                           //overridden.

class ACMEBicycle implements Bicycle {
    public void applyBrakes(){               //Here we implement applyBrakes()
       System.out.println("Brakes applied"); //function
    }
}

Example with virtual functions with abstract classes.

Similar to interfaces Abstract classes must contain virtual methods because they rely on the extending classes' implementation. For Example:

abstract class Dog {                   
    final void bark() {               //bark() is not virtual because it is 
        System.out.println("woof");   //final and if you tried to override it
    }                                 //you would get a compile time error.

    abstract void jump();             //jump() is a "pure" virtual function 
}                                     
class MyDog extends Dog{
    void jump(){
        System.out.println("boing");    //here jump() is being overridden
    }                                  
}
public class Runner {
    public static void main(String[] args) {
        Dog dog = new MyDog();       // Create a MyDog and assign to plain Dog variable
        dog.jump();                  // calling the virtual function.
                                     // MyDog.jump() will be executed 
                                     // although the variable is just a plain Dog.
    }
}
Definition answered 28/12, 2010 at 16:18 Comment(15)
This has got to be the most complete answer. It provides 2 ways to implement a virtual function since java does not have the keyword. Thank you.Lentiginous
Much better answer than the Wikipedia citation. Coming from c++ and being lazy with my Java studies, abstract was what I was looking for.Glamorous
@Glamorous How is this answer better? The wikipedia citation is complete, concise and correct. This answer, by contrast, fails to mention the elephant in the room: By default all functions in Java (with the exceptions listed in the wikipedia article) are virtual. Neither abstract classes nor interfaces are necessary for virtual functions, so that's only adding misleading noise. And then this "requires great communication skills and a deep mastery of underlying principles"... jeez. That is a self-falsifying statement right there: Nobody who had that would waste valuable disk space with it.Finzer
The wikipedia post is inferior and less specific to this answer because it is about the concept of virtual functions in any language, rather than just java. The example given in the wikipedia page is written in C, and it's an incomplete one at best, and it's more misleading. The detail about all functions being virtual, and that you don't need abstract classes or interfaces to have virtual functions being noise. I never said they are required, you misread that. I'm not understanding your final point, do you want me to delete this question because you don't like it?Definition
1. The wikipedia citation in the post starts with "In Java". One can't get any more specific than that. (The wikipedia article has since changed and doesn't contain that sentence any longer.) I'm fairly sure that the examples didn't include C, by the way. (C++ though, yes.) 2. The examples are misleading because they have no relation to Java having virtual functions by default. 3. I meant: No person who has great communication skills and deep mastery of the underlying principles would write that. I was not refering to the entire article.Finzer
The entire discussion underneath this question is not what the stackoverflow comment system was designed for. The first comment boils down to: "thanks", the second comment basically says: "It's better than something else... thanks!" and the 3rd 4th and 5th is just quibbling over whether or not this question is in fact different from some other resource on some totally unrelated site. If I could remove all six of these comments I would, because we are missing the point, which is how do I improve this post further? The upvotes have spoken, the answer is fine, the answer stays.Definition
And how is myJavaFoobarClass generic in any sense that the word carries in the realm of programming?Finzer
OK the class is not technically generic. I fixed that.Definition
I'm not quibbling. I have pointed out the following specific deficiencies of this answer. I'll repeat: 1. The answer doesn't state the most important fact which any suitable answer must provide in order to be useful. 2. It introduces two concepts (abstract classes and interfaces) which are special applications of Java polymorphism. This is misleading because the general concept (all functions are virtual anyway) is never mentioned. The reader could think that he needs an abstract class or an interface for virtual functions. [t.b.c]Finzer
[ctd] 3. I criticised, somewhat polemically, the pretentious style which is in conspicuous contrast to the poor quality of the post.-- The problem is that the post at best adds two example applications /specific constructs for Java virtual functions. These specific examples, but also much of the general explanations in the second paragraph are unnecessary if a basic programming and Java knowledge is supposed, which we can if we consider the question.Finzer
Let us continue this discussion in chat.Definition
I have edited the answer instead, making the central statement stand out, adding a plain example and eliminating the final example. (That a class or method is final does not prevent them from taking part in dynamic dispatch!).Finzer
Perhaps I phrased my comment badly. I should have prefixed it with 'For me, '. The Wikipedia post answered the question, but this post offered more detail. I was looking for the keyword 'abstract', which is what I would imagine a lot of C++ users will be looking for.Glamorous
Few years late here but fantastic answerMagalymagan
This was way back, when non-technical hiring managers were the primary deciders on who was a programmer and who wasn't. The fancy MBA's somehow got it into their tiny heads that object-oriented programming was the best thing since sliced bread, and so in order to be a good programmer, you had to just know the answer to this question and regurgitate it when he gives the signal. Even when you answered the question perfectly and timelessly, you'd still get a scowl, because that was part of their their test to make sure you were sure that you knew and you could put up with the office politics.Definition
H
60

All functions in Java are virtual by default.

You have to go out of your way to write non-virtual functions by adding the "final" keyword.

This is the opposite of the C++/C# default. Class functions are non-virtual by default; you make them so by adding the "virtual" modifier.

Hobbes answered 28/12, 2010 at 16:18 Comment(1)
private functions as stated in Klaus's answer are also non-virtual.Rendition
P
9

All non-private instance methods are virtual by default in Java.

In C++, private methods can be virtual. This can be exploited for the non-virtual-interface (NVI) idiom. In Java, you'd need to make the NVI overridable methods protected.

From the Java Language Specification, v3:

8.4.8.1 Overriding (by Instance Methods) An instance method m1 declared in a class C overrides another instance method, m2, declared in class A iff all of the following are true:

  1. C is a subclass of A.
  2. The signature of m1 is a subsignature (§8.4.2) of the signature of m2.
  3. Either * m2 is public, protected or declared with default access in the same package as C, or * m1 overrides a method m3, m3 distinct from m1, m3 distinct from m2, such that m3 overrides m2.
Predominant answered 28/12, 2010 at 16:23 Comment(0)
G
4

Yes, you can write virtual "functions" in Java.

Garbe answered 28/12, 2010 at 16:42 Comment(0)
S
1

In Java, all public (non-private) variables & functions are Virtual by default. Moreover variables & functions using keyword final are not virtual.

Strickland answered 25/9, 2016 at 0:53 Comment(1)
what do you mean by "virtual variables"?Preengage

© 2022 - 2024 — McMap. All rights reserved.