17715

Overloading a method in an immutable class

Question:

Say that I have an immutable Point class with x and y parameters, and an add method defined like this:

class Point: Point add(int x, int y): return new Point(this.x + x, this.y + y);

Since it's immutable, it returns a new Point. This is all well and good until we have a class that extends Point and redefines add.

class ColoredPoint extends Point: ColoredPoint add(int x, int y): return new ColoredPoint(this.x + x, this.y + y, this.width, this.height)

We have to write the new definition because otherwise the add method on ColoredPoint would return Point which is bad. But now this won't work in most languages because we're overriding add but we're only disambiguating on return type. Languages don't allow you to have methods that are only disambiguated on return type, because that can be ambiguous in most cases.

So what do we do?

The only solutions I see are:

<ul><li>Make them both implement some interface like IPositionable</li> <li>Give up on immutability.</li> </ul>

Anything else?

Answer1:

If you want to enforce immutability, you cannot have subclasses. See for example java.lang.String, which is a final class for this reason: To prevent people from subclassing String to make it mutable.

Also, why would Rect extend Point in the first place? Isn't it a completely different thing? Geometry-wise, they don't even exist in the same dimension.

Finally, I cannot see the connection between the problem of methods on subclasses returning a more restrained type (and some languages not supporting this well), and immutability.

Recommend

  • PHP strtotime returning false
  • Resolving explicitly the scope of a class member
  • CardLayout display Next panel - java Swing
  • Eclipse : Unknown Source Java SQL Exception
  • Maven archetype generate with custom properties
  • Why does _GET in PHP wrongly decodes slash?
  • C# Application Relative Paths
  • cURL for Windows can't make a secure connection to the Stack API
  • Cleave.js Phone CA
  • SSLRead() return error -9806/15958)
  • What distributed message queues support millions of queues?
  • How Can I Prevent Activation For Some ListView Items When The Selection Mode Is MultiChoiceModal?
  • Flex/AS3 very strange simple Number operation issue
  • How to override __call__ in celery on main?
  • how do you obtain the address of an instance after overriding the __str__ method in python
  • XNU incudes in Kext
  • Why can't I use non-integral types with switch [duplicate]
  • Prolog Ambiguous Output
  • Python getting common name from URL using ssl.getpeercert()
  • Spring integration inbound-gateway Fire an event when queue is empty
  • Salesforce Different WSDL files and when to use
  • D3 get axis values on zoom event
  • Assign variable to the value in HTML
  • VSO Build — Response status code does not indicate success: 404 (Not Found)
  • Bad request using file_get_contents for PUT request in PHP
  • OpenGL 3.3 on Mac OSX El Capitan with LWJGL
  • does jqgrid support a multiple checkbox list for editing
  • Email format validation in mvc3 view
  • C# - Is there a limit to the size of an httpWebRequest stream?
  • How to add date and time under each post in guestbook in google app engine
  • How to set/get protobuf's extension field in Go?
  • How to show dropdown in excel using jrxml (jasper api)?
  • Build own AppleScript numerical error handling
  • R: gsub and capture
  • jqPlot EnhancedLegendRenderer plugin does not toggle series for Pie charts
  • Comma separated Values
  • Android Studio and gradle
  • SQL merge duplicate rows and join values that are different
  • coudnt use logback because of log4j
  • How to load view controller without button in storyboard?