0

How would one go about overloading the getCause() method in a throwable object ? I have the following but it doesn't seem to work as it says that it cannot be overloaded with a string.

public class MyException extends RuntimeException   {
String cause;
MyException(String s)   {
    cause = s;
}
@Overwrite public String getCause()    {
    return cause;
}
Crossman
  • 278
  • 5
  • 18
  • 1
    Whats the point in overloading the `cause` property of exceptions this way? You can already supply a customized string message. The `cause` property is intended to reflect the next immediate causing exception in an *exception chain* – Perception Mar 04 '13 at 20:00

2 Answers2

2

It is illegal to have two methods that only differ in their return type. Suppose someone wrote:

Object obj = myException.getCause();

That is perfectly legal java, and the compiler has no way to figure out if it's the String version or the Throwable version.

Likewise you can't replace the superclass signature since this is also perfectly legal:

Throwable t = new MyException();
Throwable t0 = t.getCause();
//Returns String?!?!?!?
Affe
  • 47,174
  • 11
  • 83
  • 83
  • Thanks, So the only way to do this would be to change the method name ? Is there a build in way of saving the cause of the exception ? – Crossman Mar 04 '13 at 19:57
  • You didn't describe in the question your actual goal as far as a new feature, so no idea what the *this* that you're looking for a way how to do is! :) – Affe Mar 04 '13 at 20:00
  • sorry :) by saying this I mean when I throw and exception I pass the reason through as a string to be saved in the cause string, the getCause would return the cause in the catch block of my code. – Crossman Mar 04 '13 at 20:02
  • 2
    That's what `getMessage` is there for. – Affe Mar 04 '13 at 20:04
  • Thanks, so if I understand correctly the throwable object class can internally store the message by saying for example setMessage("error....") in the constructor and then just using getMessage to retrieve it ? – Crossman Mar 04 '13 at 20:06
  • it's a constructor arg, not a setter, sorry, but yes – Affe Mar 04 '13 at 20:06
1

Accepted answer clears the point :

It is illegal to have two methods that only differ in their return type

But if you have a situation where, getCause() should return the custom cause in MyException, in case original cause is null.

In that case, you can use initCause() to set the cause and override toString() method. So, when getCause() method will be called on object of MyException, it will show the message from customCause instead of null.

What is the use: In legacy system, if you have used getCause() on MyException object while logging, and now you want to add the custom cause to it without changing lot of code, here is the way.

    public class MyException extends RuntimeException {
        String customCause;

        MyException(String s) {
            super(s);
            customCause = s;
        }

        @Override
        public synchronized Throwable getCause() {
            if (super.getCause() != null) {
                return this;
            } else {
                this.initCause(new Throwable(customCause));
                return this;
            }
        }

        @Override
        public String toString() {
            String s = getClass().getName();
            String message = getLocalizedMessage();
            if (message == null) {
                message = customCause;
            }
            return (message != null) ? (s + ": " + message) : s;
        }
    }

References: https://docs.oracle.com/javase/7/docs/api/java/lang/Throwable.html#initCause(java.lang.Throwable) https://docs.oracle.com/javase/7/docs/api/java/lang/Throwable.html

Ankit Wasankar
  • 145
  • 1
  • 12