On Sat, Jun 30, 2018 at 9:40 AM, Waldek Hebisch
<[email protected]> wrote:
>>
>> On Fri, Jun 29, 2018 at 11:22 AM, Waldek Hebisch
>> <[email protected]> wrote:
>> > On command line interpreter evaluates things so can use actual
>> > values to guess what would be useful.
>>
> Bill Page wrote:
>> Yes, one should expect that the interpreter would try harder to
>> guess reasonable types in order to relieve the user of (some)
>> of this responsibility.
>>
>> > In the process it breaks several normal rules.
>> >
>> > Try:
>> >
>> > f(x) == if (x > 1) then 1
>> >                                                                    Type: 
>> > Void
>> >                                                                   Time: 0 
>> > sec
>> > (7) -> f(2)
>> >    Compiling function f with type PositiveInteger -> Void
>> >                                                                    Type: 
>> > Void
>> >                                                    Time: 0.02 (OT) = 0.02 
>> > sec
>> > (8) -> f(0)
>> >    Compiling function f with type NonNegativeInteger -> Void
>> >                                                                    Type: 
>> > Void
>> >                                                    Time: 0.01 (OT) = 0.01 
>> > sec
>> >
>> > In both cases you now get Void.
>>
>> Clearly this is a very poor (though technically correct) guess as
>> to what the user might have wanted.
>
> Maybe I should say more: compiling a function interpreter can
> _not_ use value, the function has to work for any value of
> argument, so in compiled function interpreter has to obey rules.

OK. I understand the distinction.

> In command line expression interpreter can use values.
> Sometime you get message that compilation failed, and
> that function will be interpreted.  In such case interpreter
> uses similar rules as on command line.  However, for serious
> computation such cases should be avoided because assigning
> types takes quite a lot of time.  In compiled functions this is
> done once per type, when interpreting type assignment is
> re-done on every execution of a statement.
>

Yes. There is a system command:

  )set function compile off/on  (on by default)

which is described as

  compile      compile, don't just define function bodies

but when I set function compile off, I still got the following result:

(1) -> )set function compile off
(1) -> f2(x : Integer) : Integer == if (x > 1) then 1
   Function declaration f2 : Integer -> Integer has been added to
      workspace.
                                                                   Type: Void
(2) -> f2(2)
   Compiling function f2 with type Integer -> Integer
   Conversion failed in the compiled user function f2 .

   Cannot convert the value from type Void to Integer .

--

Does this option still work? Perhaps my expectation was wrong.

>> ...
>> I cannot see any advantage in having this behavior in the
>> interpreter.
>
> Well, advantage is consistency with rules.
>

Could you site specifically what rule is being violated?

>> I think the interpreter should be changed to do the same
>> thing as the Spad compiler. The function should attempt to coerce
>> the result of the if-then expression
>>
>>   if (x > 1) then 1
>>
>> to Integer.  Of course this might cause an error for certain values
>> of x but the user is not likely to be surprised by this.
>
> Well, there are folks that want static checking, that is no type
> errors at runtime.  They prefer Void as a result type.  And
> there are folks who want to bend the rules.  IMO some sloppines
> on command line is OK.  But already for "interpreter" functions
> stricter type rules may be beneficial.
>
> Of course, having more relaxed rule in Spad compiler and stricter
> rule in intepreter is counterintuitive.  The only explanation I
> see is that original authors decided to change rules.  Remember
> that Spad is "old compiler" and compiler included in intepreter
> is "new compiler".
>

In fact the Spad compiler does not always do what I had hoped. For
example compiling the following function using Spad:

  f(x:Integer):PositiveInteger == if x<1 then 1

--

(1) -> f(0)

   (1)  1
                                                        Type: PositiveInteger
(2) -> f(1)
   Internal Error
   Interpreter code generation failed for expression(|f| 1)

--

This is a rather unexpected and obscure errror message. However it is
possible to compile explicit code such as:

  g(x:Integer):PositiveInteger == coerce((if x<1 then 1 else
void()$Void)::Union(Void,PositiveInteger))

--

2) -> g(0)

   (2)  1
                                                        Type: PositiveInteger
(3) -> g(1)

   >> Error detected within library code:
   "()" of mode Union(Void,PositiveInteger) cannot be coerced to mode
PositiveInteger

--

which does do what I had hoped, i.e. that the code generated for f
would be essentially the same as g.

-- 
You received this message because you are subscribed to the Google Groups 
"FriCAS - computer algebra system" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at https://groups.google.com/group/fricas-devel.
For more options, visit https://groups.google.com/d/optout.

Reply via email to