login  home  contents  what's new  discussion  bug reports     help  links  subscribe  changes  refresh  edit

Edit detail for #401 unparse generates Fortran function names revision 8 of 9

1 2 3 4 5 6 7 8 9
Editor: Bill Page
Time: 2008/09/02 18:57:28 GMT-7
Note: Waldek's version

added:
The patch to 'format.boot' below avoids this problem.

**On Tue, Sep 2, 2008 at 6:34 PM, Waldek Hebisch wrote:**

So I propose to apply a variation of Bill's patch.  Compared
to Bill I am using Fortran machinery only for binary operators
(like current code).  Also, I am setting a few variables used
by Fortran machinery - I do not have a testcase, but I
expect that on complicated expressions Fortran machinery
will fail if those variables have no value.

Patch::

  diff -ru --exclude=.svn trunk.bb/src/interp/format.boot trunk/src/interp/format.boot
  --- trunk.bb/src/interp/format.boot     2008-09-03 00:06:07.000000000 +0200
  +++ trunk/src/interp/format.boot        2008-09-03 00:07:38.000000000 +0200
  @@ -428,10 +428,15 @@
      argl := rest argl
      (null argl) or null (first argl) => [lo, '".."]
      [lo, '"..", form2String1 first argl]
  -  isBinaryInfix op => fortexp0 [op,:argl]
  -  -- COMPILED_-FUNCTION_-P(op) => form2String1 coerceMap2E(u1,NIL)
  +  isBinaryInfix op => binop2String [op,:argl]
    application2String(op,[form2String1 x for x in argl], u1)
 
  +binop2String x ==
  +    $exp2FortTempVarIndex : local := 0
  +    $fortName : fluid := newFortranTempVar()
  +    $fortInts2Floats : fluid := nil
  +    fortranCleanUp exp2Fort1 exp2FortOptimize x
  +
   formWrapId id ==
    $formatSigAsTeX = 1 => id
    $formatSigAsTeX = 2 =>

----

\begin{boot}
form2String1 u ==
  ATOM u => 
    u=$EmptyMode or u=$quadSymbol => formWrapId specialChar 'quad
    IDENTP u =>
      constructor? u => app2StringWrap(formWrapId u, [u])
      u
    SUBRP u => formWrapId BPINAME u
    STRINGP u => formWrapId u
    WRITE_-TO_-STRING formWrapId u
  u1 := u
  op := CAR u
  argl := CDR u
  op='Join or op= 'mkCategory => formJoin1(op,argl)
  $InteractiveMode and (u:= constructor? op) =>
    null argl => app2StringWrap(formWrapId constructorName op, u1)
    op = "NTuple"  => [ form2String1 first argl, "*"]
    op = "Map"     => ["(",:formatSignature0 [argl.1,argl.0],")"]
    op = 'Record => record2String(argl)
    null (conSig := getConstructorSignature op) =>
      application2String(constructorName op,[form2String1(a) for a in argl], u1)
    ml := rest conSig
    if not freeOfSharpVars ml then
      ml:=SUBLIS([[pvar,:val] for pvar in $FormalMapVariableList
        for val in argl], ml)
    argl:= formArguments2String(argl,ml)
      -- extra null check to handle mutable domain hack.
    null argl => constructorName op
    application2String(constructorName op,argl, u1)
  op = "Mapping" => ["(",:formatSignature argl,")"]
  op = "Record" => record2String(argl)
  op = 'Union  =>
    application2String(op,[form2String1 x for x in argl], u1)
  op = ":" =>
      null argl => [ '":" ]
      null rest argl => [ '":", form2String1 first argl ]
      formDecl2String(argl.0,argl.1)
  op = "#" and PAIRP argl and LISTP CAR argl =>
    STRINGIMAGE SIZE CAR argl
  op = 'Join => formJoin2String argl
  op = "ATTRIBUTE" => form2String1 first argl
  op='Zero => 0
  op='One => 1
  op = 'AGGLST => tuple2String argl
  op = 'BRACKET =>
    argl' := form2String1 first argl
    ["[",:(atom argl' => [argl']; argl'),"]"]
  op = "SIGNATURE" =>
     [operation,sig] := argl
     concat(operation,": ",formatSignature sig)
  op = 'COLLECT => formCollect2String argl
  op = 'construct =>
    concat(lbrkSch(),
           tuple2String [form2String1 x for x in argl],rbrkSch())
  op = "SEGMENT" =>
    null argl => '".."
    lo := form2String1 first argl
    argl := rest argl
    (null argl) or null (first argl) => [lo, '".."]
    [lo, '"..", form2String1 first argl]
    isBinaryInfix op => binop2String [op,:argl]
    application2String(op,[form2String1 x for x in argl], u1)
 
binop2String x ==
    $exp2FortTempVarIndex : local := 0
    $fortName : fluid := newFortranTempVar()
    $fortInts2Floats : fluid := nil
    fortranCleanUp exp2Fort1 exp2FortOptimize x
\end{boot}

Let's try it ...
\begin{axiom}
y := cos(x2) + 2*x1
ys := unparse(y::INFORM)
test(parse(ys)::Expression Integer = y)
x := sqrt(x2/x1)
test(parse(unparse(x::INFORM))::Expression Integer = x)
unparse(parse("exp(z+1)")::Expression Integer::INFORM)="exp(z+1)"
test %
unparse(parse("1/exp(z+1)")::Expression Integer::INFORM)="1/exp(z+1)"
test %
\end{axiom}

Did I do something wrong in applying the patch?

Submitted by : page at: 2007-11-12T16:57:33-08:00 (17 years ago)
Name :
Axiom Version :
Category : Severity : Status :
Optional subject :  
Optional comment :

In an email with subject:

  Axiom: Printing multiple variables in axiom.

to axiom-math on Nov 11, 2007 3:10 PM Constantine Frangos reported that:

I am getting the result below for y.

However, the output I actually want is:

  "cos(x2) + 2*x1"

or even better:

  cos(x2) + 2*x1

Is this possible ?

axiom
y := cos(x2) + 2*x1
LatexWiki Image(1)
Type: Expression Integer
axiom
unparse(y::INFORM)
LatexWiki Image(2)
Type: String

I think the problem originats in the routine form2String1 which is called via form2String from unparse. form2String1 calls fortexp0 defined in newfort.boot. This routine calls expression2Fortran which transforms the InputForm? via:

  fortranCleanUp exp2Fort1 segment fortPre exp2FortOptimize outputTran e

fortPre is responsible for renaming functions like cos to DCOS for Fortran double or single float compatibility in a routine called mkFortFn. segment is intended to handle lines longer than allowed in Fortran, and outputTran renames some operations to be subsequently remapped by fortPre to the appropriate operator depending on the precision setting. None of this is necessary if the intention is to "unparse" an Axiom expression.

The patch to format.boot below avoids this problem.

boot
form2String1 u ==
  ATOM u => 
    u=$EmptyMode or u=$quadSymbol => formWrapId specialChar 'quad
    IDENTP u =>
      constructor? u => app2StringWrap(formWrapId u, [u])
      u
    SUBRP u => formWrapId BPINAME u
    STRINGP u => formWrapId u
    WRITE_-TO_-STRING formWrapId u
  u1 := u
  op := CAR u
  argl := CDR u
  op='Join or op= 'mkCategory => formJoin1(op,argl)
  $InteractiveMode and (u:= constructor? op) =>
    null argl => app2StringWrap(formWrapId constructorName op, u1)
    op = "NTuple"  => [ form2String1 first argl, "*"]
    op = "Map"     => ["(",:formatSignature0 [argl.1,argl.0],")"]
    op = 'Record => record2String(argl)
    null (conSig := getConstructorSignature op) =>
      application2String(constructorName op,[form2String1(a) for a in argl], u1)
    ml := rest conSig
    if not freeOfSharpVars ml then
      ml:=SUBLIS([[pvar,:val] for pvar in $FormalMapVariableList
        for val in argl], ml)
    argl:= formArguments2String(argl,ml)
      -- extra null check to handle mutable domain hack.
    null argl => constructorName op
    application2String(constructorName op,argl, u1)
  op = "Mapping" => ["(",:formatSignature argl,")"]
  op = "Record" => record2String(argl)
  op = 'Union  =>
    application2String(op,[form2String1 x for x in argl], u1)
  op = ":" =>
      null argl => [ '":" ]
      null rest argl => [ '":", form2String1 first argl ]
      formDecl2String(argl.0,argl.1)
  op = "#" and PAIRP argl and LISTP CAR argl =>
    STRINGIMAGE SIZE CAR argl
  op = 'Join => formJoin2String argl
  op = "ATTRIBUTE" => form2String1 first argl
  op='Zero => 0
  op='One => 1
  op = 'AGGLST => tuple2String argl
  op = 'BRACKET =>
    argl' := form2String1 first argl
    ["[",:(atom argl' => [argl']; argl'),"]"]
  op = "SIGNATURE" =>
     [operation,sig] := argl
     concat(operation,": ",formatSignature sig)
  op = 'COLLECT => formCollect2String argl
  op = 'construct =>
    concat(lbrkSch(),
           tuple2String [form2String1 x for x in argl],rbrkSch())
  op = "SEGMENT" =>
    null argl => '".."
    lo := form2String1 first argl
    argl := rest argl
    (null argl) or null (first argl) => [lo, '".."]
    [lo, '"..", form2String1 first argl]
  --isBinaryInfix op => fortexp0 [op,:argl]
  fortranCleanUp exp2Fort1 exp2FortOptimize [op,:argl]
  -- COMPILED_-FUNCTION_-P(op) => form2String1 coerceMap2E(u1,NIL)
  --application2String(op,[form2String1 x for x in argl], u1)
boot
Value = T
Value = 6840

The function:

  parse(s)==interpret(ncParseFromString(s)$Lisp::INFORM)

parses abd evaluates a string s, returning the result as ANY. We can use this to test that unparse

axiom
parse(s)==interpret(ncParseFromString(s)$Lisp::INFORM)
Type: Void
axiom
y := cos(x2) + 2*x1
LatexWiki Image(3)
Type: Expression Integer
axiom
ys := unparse(y::INFORM)
LatexWiki Image(4)
Type: String
axiom
test(parse(ys)::Expression Integer = y)
axiom
Compiling function parse with type String -> Any
LatexWiki Image(5)
Type: Boolean
axiom
x := sqrt(x2/x1)
LatexWiki Image(6)
Type: Expression Integer
axiom
test(parse(unparse(x::INFORM))::Expression Integer = x)
LatexWiki Image(7)
Type: Boolean
axiom
unparse(parse("exp(z+1)")::Expression
Integer::INFORM)="exp(z+1)"
LatexWiki Image(8)
Type: Equation String
axiom
test %
LatexWiki Image(9)
Type: Boolean
axiom
unparse(parse("1/exp(z+1)")::Expression
Integer::INFORM)="1/exp(z+1)"
LatexWiki Image(10)
Type: Equation String
axiom
test %
LatexWiki Image(11)
Type: Boolean

same problem occurs in graphics --page, Mon, 12 Nov 2007 18:25:31 -0800 reply
The display of function names in legends generated by Axiom graphics also suffers from Fortranish names like DSIN etc. The patch to format.boot above also fixes that.

Status: open => fix proposed

The patch to format.boot below avoids this problem.

On Tue, Sep 2, 2008 at 6:34 PM, Waldek Hebisch wrote:

So I propose to apply a variation of Bill's patch. Compared to Bill I am using Fortran machinery only for binary operators (like current code). Also, I am setting a few variables used by Fortran machinery - I do not have a testcase, but I expect that on complicated expressions Fortran machinery will fail if those variables have no value.

Patch:

  diff -ru --exclude=.svn trunk.bb/src/interp/format.boot trunk/src/interp/format.boot
  --- trunk.bb/src/interp/format.boot     2008-09-03 00:06:07.000000000 +0200
  +++ trunk/src/interp/format.boot        2008-09-03 00:07:38.000000000 +0200
  @@ -428,10 +428,15 @@
      argl := rest argl
      (null argl) or null (first argl) => [lo, '".."]
      [lo, '"..", form2String1 first argl]
  -  isBinaryInfix op => fortexp0 [op,:argl]
  -  -- COMPILED_-FUNCTION_-P(op) => form2String1 coerceMap2E(u1,NIL)
  +  isBinaryInfix op => binop2String [op,:argl]
    application2String(op,[form2String1 x for x in argl], u1)

  +binop2String x ==
  +    $exp2FortTempVarIndex : local := 0
  +    $fortName : fluid := newFortranTempVar()
  +    $fortInts2Floats : fluid := nil
  +    fortranCleanUp exp2Fort1 exp2FortOptimize x
  +
   formWrapId id ==
    $formatSigAsTeX = 1 => id
    $formatSigAsTeX = 2 =>

----

boot
form2String1 u ==
  ATOM u => 
    u=$EmptyMode or u=$quadSymbol => formWrapId specialChar 'quad
    IDENTP u =>
      constructor? u => app2StringWrap(formWrapId u, [u])
      u
    SUBRP u => formWrapId BPINAME u
    STRINGP u => formWrapId u
    WRITE_-TO_-STRING formWrapId u
  u1 := u
  op := CAR u
  argl := CDR u
  op='Join or op= 'mkCategory => formJoin1(op,argl)
  $InteractiveMode and (u:= constructor? op) =>
    null argl => app2StringWrap(formWrapId constructorName op, u1)
    op = "NTuple"  => [ form2String1 first argl, "*"]
    op = "Map"     => ["(",:formatSignature0 [argl.1,argl.0],")"]
    op = 'Record => record2String(argl)
    null (conSig := getConstructorSignature op) =>
      application2String(constructorName op,[form2String1(a) for a in argl], u1)
    ml := rest conSig
    if not freeOfSharpVars ml then
      ml:=SUBLIS([[pvar,:val] for pvar in $FormalMapVariableList
        for val in argl], ml)
    argl:= formArguments2String(argl,ml)
      -- extra null check to handle mutable domain hack.
    null argl => constructorName op
    application2String(constructorName op,argl, u1)
  op = "Mapping" => ["(",:formatSignature argl,")"]
  op = "Record" => record2String(argl)
  op = 'Union  =>
    application2String(op,[form2String1 x for x in argl], u1)
  op = ":" =>
      null argl => [ '":" ]
      null rest argl => [ '":", form2String1 first argl ]
      formDecl2String(argl.0,argl.1)
  op = "#" and PAIRP argl and LISTP CAR argl =>
    STRINGIMAGE SIZE CAR argl
  op = 'Join => formJoin2String argl
  op = "ATTRIBUTE" => form2String1 first argl
  op='Zero => 0
  op='One => 1
  op = 'AGGLST => tuple2String argl
  op = 'BRACKET =>
    argl' := form2String1 first argl
    ["[",:(atom argl' => [argl']; argl'),"]"]
  op = "SIGNATURE" =>
     [operation,sig] := argl
     concat(operation,": ",formatSignature sig)
  op = 'COLLECT => formCollect2String argl
  op = 'construct =>
    concat(lbrkSch(),
           tuple2String [form2String1 x for x in argl],rbrkSch())
  op = "SEGMENT" =>
    null argl => '".."
    lo := form2String1 first argl
    argl := rest argl
    (null argl) or null (first argl) => [lo, '".."]
    [lo, '"..", form2String1 first argl]
    isBinaryInfix op => binop2String [op,:argl]
    application2String(op,[form2String1 x for x in argl], u1)
binop2String x == $exp2FortTempVarIndex : local := 0 $fortName : fluid := newFortranTempVar() $fortInts2Floats : fluid := nil fortranCleanUp exp2Fort1 exp2FortOptimize x
boot
Value = T
Value = 7960

Let's try it ...

axiom
y := cos(x2) + 2*x1
LatexWiki Image(12)
Type: Expression Integer
axiom
ys := unparse(y::INFORM)
>> Error detected within library code: strsym: form is neither a string or symbol

Did I do something wrong in applying the patch?