Unit values

Adde adde at trialcode.com
Wed Apr 27 15:01:23 PDT 2005


Brian Rice wrote:

> On Apr 27, 2005, at 2:02 PM, Adde wrote:
>
>> Brian Rice wrote:
>>
>>> I think the attention you two have given this library has reached a 
>>> threshhold. If you read the source, you'll see that I just ported it 
>>> from Smalltalk-80 and didn't care too much about it.
>>>
>>> Right now, you two care more about it than I do. So put your fingers 
>>> where your mouth is, and code up these changes yourself and use 
>>> darcs send so I can apply them.
>>>
>>> Patches speak louder than words! :)
>>>
>>> On Apr 27, 2005, at 7:41 AM, David Hopwood wrote:
>>>
>>>> Suggestion: merge the UnitValue and Unit types, by having a unit 
>>>> behave
>>>> as 1 of that unit, i.e. px = 1*px.
>>>>
>>>> Then only multiplication is needed to form a UnitValue, e.g. 42*px.
>>>> Similarly examples like "(72*px) / in" would work automatically. This
>>>> design also allows derived units and conversion factors to be 
>>>> expressed
>>>> more simply.
>>>
>> I'm fine with implementing the changes myself if and when I feel I 
>> understand the problem well enough.
>> One thing I'm wondering that has nothing to do with the Units library 
>> is if there is any way to dispatch on a slot of an object.
>> Something like this maybe:
>>
>> uv unit@(Pixel traits) printOn: p@(SVG Printer traits) [
>>  uv value printOn: p.
>>  uv unit printOn: p.
>> ].
>>
>> And if that isn't possible, do you think it'd be a good idea to add a 
>> slot to BaseUnit that contains the base for it's values so that you 
>> can dispatch on that instead? It wouldn't mean any changes to the 
>> code using the library since BaseUnit could init the slot itself. 
>> Then you cold do things like this:
>>
>> uv@(Pixel baseValue traits) printOn: p@(SVG Printer traits) [
>>  uv value printOn: p.
>>  uv unit printOn: p.
>> ].
>
>
> Dispatching on slot-values is basically dynamic pattern-matching. This 
> is problematic mostly for performance reasons, but also your syntax 
> and methodology for this definition is unsound. Slate is one step away 
> from this level of semantics for a good reason...
>
> What you're failing to grasp is that what follows the @ is just 
> another Slate expression which happens to annotate the argument name 
> you've specified, so "Pixel baseValue traits" will get you the traits 
> object of whatever is returned by sending baseValue to Pixel, not by 
> sending baseValue to uv. Furthermore, uv is the argument of the 
> message, not its baseValue. The fact that Slate has no special syntax 
> here is a hard limit to what we can do this way. You just can't 
> dispatch on something that's not an argument in Slate. As far as I can 
> tell, you have to choose between simple, flexible syntax (Slate) and 
> being able to do pattern-match-y things (Cecil, Haskell, etc.) by 
> using a baroque syntax.
>
> Maybe Lee has some ideas on how to admit pattern-matching-like 
> semantics to Slate, since he's given it a little thought, but don't 
> count on this any time soon (i.e. before we bootstrap into a much less 
> concrete syntax, and even then don't expect us to go the route of 
> languages "with declarations" like Haskell or Java).
>
> -- 
> Brian T. Rice
> LOGOS Research and Development
> http://tunes.org/~water/
>
I think I confused you a bit by mentioning dispatching on slots, forget 
I mentioned that, it was just a crazy idea ;)
'Pixel baseValue traits' is exactly the object i want, if 'uv' is cloned 
from 'Pixel baseValue' then it's a Pixel value.
Load the following:

Ensurenamespace: #Test.

Test addPrototype: #UnitValue derivedFrom: {Cloneable}.
Test UnitValue addSlot: #unit.
Test UnitValue addSlot: #value.

Test addPrototype: #BaseUnit derivedFrom: {Cloneable}.
Test BaseUnit addSlot: #name.
Test BaseUnit addSlot: #abbrev.
Test BaseUnit addSlot: #baseValue.

bu@(Test BaseUnit) name: n abbrev: a [ |u|
  u: Test BaseUnit clone `>> [name: n. abbrev: a.].
  u baseValue: (Test UnitValue clone `>> [unit: u.]).
  u
].

Test addImmutableSlot: #Pixel valued: (Test BaseUnit name: 'pixel' 
abbrev: 'px').

n@(Number traits) px [
  Test Pixel baseValue clone `>> [value: n.]
].

uv@(Test Pixel baseValue traits) toXML [
  'This is printed because uv is a Pixel value, ie. cloned from Pixel 
baseValue'
].

and then execute this:
(1 px) toXML.

Instead of cloning UnitValue when creating new Pixel Values you only 
have to make sure that you clone Pixel baseValue instead.

/Adde




More information about the Slate mailing list