Re: Mixing OO and DB
Date: Mon, 18 Feb 2008 05:58:06 -0800 (PST)
Message-ID: <d927af87-5038-4da9-ac27-cedaf63a8840_at_s37g2000prg.googlegroups.com>
On Feb 18, 7:23 pm, "Dmitry A. Kazakov" <mail..._at_dmitry-kazakov.de>
wrote:
> On Sun, 17 Feb 2008 21:56:18 -0800 (PST), David BL wrote:
> > On Feb 16, 9:03 pm, "Dmitry A. Kazakov" <mail..._at_dmitry-kazakov.de>
> > wrote:
> >> I mean that you need not to resort to pointers or more generally to
> >> internal representation in order to say that Rectangle value can be
> >> obtained from a ColouredRectangle one.
>
> > Agreed. However note firstly that I introduced pointers in order to
> > talk about substitutability of variables. Secondly, I don't deny it's
> > *possible* to obtain a Rectangle value from a ColouredRectangle one.
> > I don't think this should ever happen implicitly.
>
> Why not, If you can do it safely?
I believe implicit conversions should be information preserving.
> >>> Perhaps the C.Date approach needs a different terminology (ie than
> >>> subtype) to avoid this confusion. When Date says integers is a sub-
> >>> type of reals, he means for example that nonzero integers have
> >>> inherited real-valued multiplicative inverses. In mathematical
> >>> definitions of integers that's inappropriate, but for software
> >>> development I need to see a good reason to disallow it. Can you
> >>> provide one?
>
> >> No, it is OK. That is a specialization. You constrain a type upon
> >> subtyping. The constraining manifests by loosing some operations. There is
> >> nothing wrong with that. But also there is nothing wrong with
> >> generalization. And also there is nothing wrong with mixed cases.
>
> > With C.Date's notion of sub-type you always inherit all operations
> > from the super-type. You can add more operations, but cannot lose any
> > (or redefine any).
>
> > For example, if 16 bit integers subtype 32 bit integers, then 16 bit
> > integers inherit addition modulo 2^32 (stored in a 32 bit result).
> > That doesn't stop 16 bit integers from introducing addition modulo
> > 2^16 as a distinct operator. Overloading of operator+ is just a
> > syntactic issue.
>
> It is not. The user of 16-bit integer has to know which + to take. As a
> counter example consider big and little endian encoded integers. One is a
> subtype of another. Now you have two overloaded operations + (actually more
> for mixed cases) one of them is rubbish.
> Note. What C.Date aims at, is easily solved by the position 4 below. When
> you dispatch to 2^32 operation, it is a 2^32 value there. No further
> dispatch happens and the proper + gets selected.
>
> >>> I don't think you need the mapping to give an ellipse value from a
> >>> circle value. I would rather say the set of circle values is a subset
> >>> of the set of ellipse values.
>
> >> Disagree, that would heavily limit the system, and likely make it
> >> inconsistent. The only sense in which circle value should ellipse value is
> >> to keep the internal representation same. Why should I care?
>
> > It doesn't limit the system in the way you suggest. You can have many
> > different representations of the same (logical) value. For example
> > polar versus cartesian representation of a point.
>
> OK, but then "same logical value" is merely a class of equivalence of some
> "physical values." My point is that the latter are fundamental while the
> former are derived. .
I think we're coming at this from different directions. You want to start with the physical implementation and ask what it maps to at some logical level - almost like reverse engineering! I want to do the reverse which is more like design. My approach is more restrictive - but IMO for good reasons.
I suggest a value type is by definition a set of (logical) values plus operators on those values. There is no such thing as "physical values". When a programmer defines a concrete type it is necessary to provide at least one physical implementation. I have generally been ignoring that in all our discussions about value-types and subtyping.
A physical representation is generally something to be hidden away, so that users of the type deal with it *only* at the logical level. Users can specify values and use all the operators, including the test for value equivalence. There can only be one definition of equivalence of values of a given type. If another notion of value equivalence is required then a distinct type must be defined.
> Note that this is same as in mathematics where Q
> "contains" Z, while members of Q aren't numbers at all, but sets of ordered
> pairs
> > I can imagine a language with the same goals for run time efficiency
> > as C++, and the following function can be compiled for many different
> > implementations of Rectangle, including specialisations like Square or
> > UnitSquare.
>
> > float GetArea(Rectangle r)
> > {
> > return r.Width() * r.Height();
> > }
>
> Yes, but to be able to judge about *different* representations you have to
> make them distinct things => different values. First you have shown
> equivalence, you can forget about differences. But not before that.
> >>>> As for subtyping, to me, it is just a relation between types. I don't
> >>>> expect it to deliver substitutability. It cannot. What it can and should,
> >>>> is to help me to deal with the problem.
>
> >>> Can it? I'm interested to know what you have in mind.
>
> >> There are many cases where languages could be safer. For example:
>
> >> 1. multiple dispatching should ensure overriding of all cross variants
> >> (dispatch may not fail).
>
> > I wonder whether dynamic dispatch is only relevant to the LSP notion
> > of sub-typing, ie not to value types. Perhaps not, because union
> > value-types seem to need it.
>
> If you want to have classes of values, these will be polymorphic values,
> which shall dispatch. Consider:
>
> class Boolean
> {
> public :
> virtual String Image () // returns "true" or "false"
>
> };
>
> class Tristate : public Boolean
> {
> public :
> virtual String Image (); // returns "true", "false", "unknown"
>
> };
[snip] Received on Mon Feb 18 2008 - 14:58:06 CET