Java Questions 31 - 40  «Prev  Next»

Return Types and Object Construction in Java SE 25

Explore covariant returns, method signatures, constructor declarations, and the stages of object initialization.

  1. Does an overloaded method have to retain another overload's return type?

    Answer: No. Distinct overloads may have different return types, provided their parameter signatures are legally different. Each method body must still return a value compatible with its own declaration, or use the rules for a void method.

    Return type alone cannot distinguish overloads. Declaring both int size() and long size() in the same class is illegal. A caller's desired assignment type does not rescue that pair of declarations.

  2. What is the difference between arguments and parameters?

    Answer: Parameters are variables declared in a method or constructor's parameter list. Arguments are the expressions supplied by a call. In int add(int left, int right), left and right are parameters; in add(2, count), 2 and count are argument expressions.

    Java evaluates argument expressions from left to right and passes their values by value. For references, that means copying the reference value, not copying the object and not allowing a parameter reassignment to replace the caller's variable.

  3. Which requirements must an overriding method meet?

    Answer: It must override an eligible instance method with a compatible signature and return type. It cannot reduce accessibility or broaden the permitted checked exceptions. Private methods are not overridden, and final methods prohibit overriding.

    "Match everything exactly" is too strong: covariant reference returns and wider access are allowed. Generic signature rules also matter. Use @Override to have the compiler verify the intended relationship, then verify that the behavior respects the supertype's contract.


  4. What is a covariant return type?

    Answer: It permits an overriding method to return a more specific reference type than the method it overrides. This supports a specialized API without requiring callers of the specialized declaration to cast the result.

    public class CovariantCopy {
        static class Document {
            Document copy() { return new Document(); }
        }
        static class Invoice extends Document {
            @Override Invoice copy() { return new Invoice(); }
        }
        public static void main(String[] args) {
            Invoice first = new Invoice();
            Invoice second = first.copy();
            Document general = first;
            Document third = general.copy();
            System.out.println(second.getClass().getSimpleName());
            System.out.println(third.getClass().getSimpleName());
        }
    }

    Both lines print Invoice. The call through general has compile-time result type Document, even though the runtime result is an Invoice. Covariance does not make every caller automatically see the narrower return type.

  5. How does the return type participate in overloading and overriding?

    Answer: In overloading, distinct parameter signatures allow independently chosen return types. In overriding, the return declaration must be compatible with the overridden method, including permitted covariant reference returns.

    The subtype relationship is between the return types, not between “an overridden method and a class.” For example, Invoice can be a subtype of Document; methods themselves are not subclasses of classes.


  6. Can an override change a primitive return type?

    Answer: No. An override of an int-returning method must return int, not long, Integer, or another type. Numeric widening and boxing do not create covariant primitive returns.

    A method overriding a void method must also have a void result. Reference covariance is a separate rule and should not be generalized to every conversion that is valid in an assignment.


  7. Does creating every kind of Java object require an ordinary constructor call?

    Answer: Ordinary class-instance creation with new invokes a constructor chain. However, arrays are objects and do not invoke class constructors in that way. Cloning and deserialization also have specialized creation rules.

    Therefore, “no object can exist without calling its constructor” is an overstatement. When discussing constructors, specify ordinary class-instance creation rather than applying that rule to every object-creation mechanism.

  8. How is an ordinary new class instance initialized?

    Answer: Storage is allocated and instance fields first receive default values. Constructor processing then performs superclass construction, instance field initializers and initializer blocks, and constructor statements in the order prescribed by the language.

    Java SE 25 allows a restricted prologue before an explicit this or super constructor invocation, including permitted initialization of the current class's fields. This makes a simple “super must always be the first statement” description obsolete. Calling a superclass constructor initializes the same object; it does not allocate a separate parent object.



  9. Do classes, including abstract classes, have constructors?

    Answer: Yes, class construction uses constructors, whether explicitly declared or supplied under the relevant language rules. An ordinary class without a constructor declaration gets a default constructor. An abstract class can declare constructors used during subclass construction, even though the abstract class cannot be directly instantiated.

    Records, enums, anonymous classes, and implicitly declared classes have specialized rules. Interfaces do not declare constructors. Do not assume every class gets an accessible no-argument constructor.

  10. What are the basic syntax rules for a constructor declaration?

    Answer: An explicitly declared constructor uses the class's simple name and has no return type, not even void. A declaration such as void Widget() inside Widget is a method, not a constructor.

    Constructors may be overloaded and may declare checked exceptions. Records also support compact canonical constructor syntax, which omits the parameter list while retaining the record's name. Constructors are neither inherited nor overridden.

References: JLS: methods and constructors, JLS: instance creation, and Flexible constructor bodies.


SEMrush Software