Skip to content

Commit

Permalink
removing the numerical comparison test. Adding an explanation at the …
Browse files Browse the repository at this point in the history
…beginning of the file
  • Loading branch information
mmatera committed Dec 3, 2024
1 parent 90aef9b commit 46694ea
Showing 1 changed file with 36 additions and 293 deletions.
329 changes: 36 additions & 293 deletions test/test_mathics_precedence.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,40 @@
"""
Test precedences
================
Precedence values reported in the Mathics Scanner tables do not always match
with the values reported by `Precedence[...]` in WMA. As it was
pointed out by Robert L. Jacobson in
[https://www.robertjacobson.dev/posts/2018-09-03-generalizing-pemdas-what-is-an-operator/]
and [https://www.robertjacobson.dev/posts/2018-09-04-defining-the-wolfram-language-part-2-operator-properties/]
The behavior of the parser and the formatter of WMA do not always is consistent with the values
reported by `Precedence[...]`. Jacobson mentions that in the most of the cases, the behaviour is more
consistent with the values reported by `WolframLanguageData`, which are given following a different
numeric convention.
Some examples of these inconsistencies are:
* In WMA, `Precedence` reports the same value (215) for all the boolean operators
(`Not`, `And`, `Nand`, `Xor`, `Or`, `Nor`) but behaves as
```
Precedence[Not]>Precedence[And]==Precedence[Nand]>Precedence[Xor]>Precedence[Or]==Precedence[Nor]
```
In other cases, precedence values of some operators are reported to be the default value (670)
while its behaviour is different (Ej: `GreaterSlantEqual` and `LessSlantEqual` behaves as
their precedence were the same that the one for `LessEqual` and `GreaterEqual`).
In any case, the relevant information is the order relation that `Precedence` induce over the
operator and their associated symbols, and this is the information that we want to curate in
the MathicsScanner tables.
This module test that the *order* induced by the precedence values assigned to each operator/symbol
to be consistent with the one of a list built from WMA. This list was build by sorting the elements
according to their WMA `Precedence` values, and then modified in a way the ordering be consistent
with the way in which expressions involving these symbols / operators are parsed and formatter
by `OutputForm`. This consistency was tested in WMA using the functions defined in
the `testprecedence.m` module.
"""

try:
Expand All @@ -11,265 +46,6 @@

import pytest

WMA_PRECEDENCES = {
"CompoundExpression": 10.0,
"Put": 30.0,
"PutAppend": 30.0,
"Set": 40.0,
"SetDelayed": 40.0,
"UpSet": 40.0,
"UpSetDelayed": 40.0,
"Because": 50.0,
"Therefore": 50.0,
"Postfix": 70.0,
"Colon": 80.0,
"Function": 90.0,
"AddTo": 100.0,
"DivideBy": 100.0,
"SubtractFrom": 100.0,
"TimesBy": 100.0,
"ReplaceAll": 110.0,
"ReplaceRepeated": 110.0,
"RuleDelayed": 120.0,
"Rule": 120.0,
"Condition": 130.0,
"StringExpression": 135.0,
"Optional": 140.0,
"Alternatives": 160.0,
"Repeated": 170.0,
"RepeatedNull": 170.0,
"SuchThat": 180.0,
"DoubleLeftTee": 190.0,
"DoubleRightTee": 190.0,
"DownTee": 190.0,
"LeftTee": 190.0,
"Perpendicular": 190.0,
"RightTee": 190.0,
"UpTee": 190.0,
"Implies": 200.0,
"Equivalent": 205.0,
"And": 215.0,
"Nand": 215.0,
"Nor": 215.0,
"Or": 215.0,
"Xor": 215.0,
"Not": 230.0,
"RoundImplies": 240.0,
"NotReverseElement": 250.0,
"NotSquareSubsetEqual": 250.0,
"NotSquareSupersetEqual": 250.0,
"NotSubset": 250.0,
"NotSubsetEqual": 250.0,
"NotSuperset": 250.0,
"NotSupersetEqual": 250.0,
"ReverseElement": 250.0,
"SquareSubset": 250.0,
"SquareSubsetEqual": 250.0,
"SquareSuperset": 250.0,
"SquareSupersetEqual": 250.0,
"Subset": 250.0,
"SubsetEqual": 250.0,
"Superset": 250.0,
"SupersetEqual": 250.0,
"DoubleLeftArrow": 270.0,
"DoubleLeftRightArrow": 270.0,
"DoubleRightArrow": 270.0,
"DownLeftRightVector": 270.0,
"DownLeftTeeVector": 270.0,
"DownLeftVector": 270.0,
"DownLeftVectorBar": 270.0,
"DownRightTeeVector": 270.0,
"DownRightVector": 270.0,
"DownRightVectorBar": 270.0,
"LeftArrow": 270.0,
"LeftArrowBar": 270.0,
"LeftArrowRightArrow": 270.0,
"LeftRightArrow": 270.0,
"LeftRightVector": 270.0,
"LeftTeeArrow": 270.0,
"LeftTeeVector": 270.0,
"LeftVector": 270.0,
"LeftVectorBar": 270.0,
"LowerLeftArrow": 270.0,
"LowerRightArrow": 270.0,
"RightArrow": 270.0,
"RightArrowBar": 270.0,
"RightArrowLeftArrow": 270.0,
"RightTeeArrow": 270.0,
"RightTeeVector": 270.0,
"RightVector": 270.0,
"RightVectorBar": 270.0,
"ShortLeftArrow": 270.0,
"ShortRightArrow": 270.0,
"UpperLeftArrow": 270.0,
"UpperRightArrow": 270.0,
"DoubleVerticalBar": 280.0,
"NotDoubleVerticalBar": 280.0,
"VerticalBar": 280.0,
"Equal": 290.0,
"Greater": 290.0,
"GreaterEqual": 290.0,
"Less": 290.0,
"LessEqual": 290.0,
"SameQ": 290.0,
"Unequal": 290.0,
"UnsameQ": 290.0,
"Congruent": 290.0,
"CupCap": 290.0,
"DotEqual": 290.0,
"EqualTilde": 290.0,
"Equilibrium": 290.0,
"GreaterEqualLess": 290.0,
"GreaterFullEqual": 290.0,
"GreaterGreater": 290.0,
"GreaterLess": 290.0,
"GreaterTilde": 290.0,
"HumpDownHump": 290.0,
"HumpEqual": 290.0,
"LeftTriangle": 290.0,
"LeftTriangleBar": 290.0,
"LeftTriangleEqual": 290.0,
"LessEqualGreater": 290.0,
"LessFullEqual": 290.0,
"LessGreater": 290.0,
"LessLess": 290.0,
"LessTilde": 290.0,
"NestedGreaterGreater": 290.0,
"NestedLessLess": 290.0,
"NotCongruent": 290.0,
"NotCupCap": 290.0,
"NotGreater": 290.0,
"NotGreaterEqual": 290.0,
"NotGreaterFullEqual": 290.0,
"NotGreaterLess": 290.0,
"NotGreaterTilde": 290.0,
"NotLeftTriangle": 290.0,
"NotLeftTriangleEqual": 290.0,
"NotLess": 290.0,
"NotLessEqual": 290.0,
"NotLessFullEqual": 290.0,
"NotLessGreater": 290.0,
"NotLessTilde": 290.0,
"NotPrecedes": 290.0,
"NotPrecedesSlantEqual": 290.0,
"NotPrecedesTilde": 290.0,
"NotRightTriangle": 290.0,
"NotRightTriangleEqual": 290.0,
"NotSucceeds": 290.0,
"NotSucceedsSlantEqual": 290.0,
"NotSucceedsTilde": 290.0,
"NotTilde": 290.0,
"NotTildeEqual": 290.0,
"NotTildeFullEqual": 290.0,
"NotTildeTilde": 290.0,
"Precedes": 290.0,
"PrecedesEqual": 290.0,
"PrecedesSlantEqual": 290.0,
"PrecedesTilde": 290.0,
"Proportion": 290.0,
"Proportional": 290.0,
"ReverseEquilibrium": 290.0,
"RightTriangle": 290.0,
"RightTriangleBar": 290.0,
"RightTriangleEqual": 290.0,
"Succeeds": 290.0,
"SucceedsEqual": 290.0,
"SucceedsSlantEqual": 290.0,
"SucceedsTilde": 290.0,
"Tilde": 290.0,
"TildeEqual": 290.0,
"TildeFullEqual": 290.0,
"TildeTilde": 290.0,
"DirectedEdge": 295.0,
"UndirectedEdge": 295.0,
"SquareUnion": 300.0,
"UnionPlus": 300.0,
"Span": 305.0,
"SquareIntersection": 305.0,
"MinusPlus": 310.0,
"PlusMinus": 310.0,
"Plus": 310.0,
"Subtract": 310.0,
"CircleMinus": 330.0,
"CirclePlus": 330.0,
"Cup": 340.0,
"Cap": 350.0,
"Coproduct": 360.0,
"VerticalTilde": 370.0,
"Star": 390.0,
"Times": 400.0,
"CenterDot": 410.0,
"CircleTimes": 420.0,
"Vee": 430.0,
"Wedge": 440.0,
"Diamond": 450.0,
"Backslash": 460.0,
"Divide": 470.0,
"Minus": 480.0,
"Dot": 490.0,
"CircleDot": 520.0,
"SmallCircle": 530.0,
"Square": 540.0,
"CapitalDifferentialD": 550.0,
"Del": 550.0,
"DifferentialD": 550.0,
"DoubleDownArrow": 580.0,
"DoubleLongLeftArrow": 580.0,
"DoubleLongLeftRightArrow": 580.0,
"DoubleLongRightArrow": 580.0,
"DoubleUpArrow": 580.0,
"DoubleUpDownArrow": 580.0,
"DownArrow": 580.0,
"DownArrowBar": 580.0,
"DownArrowUpArrow": 580.0,
"DownTeeArrow": 580.0,
"LeftDownTeeVector": 580.0,
"LeftDownVector": 580.0,
"LeftDownVectorBar": 580.0,
"LeftUpDownVector": 580.0,
"LeftUpTeeVector": 580.0,
"LeftUpVector": 580.0,
"LeftUpVectorBar": 580.0,
"LongLeftArrow": 580.0,
"LongLeftRightArrow": 580.0,
"LongRightArrow": 580.0,
"ReverseUpEquilibrium": 580.0,
"RightDownTeeVector": 580.0,
"RightDownVector": 580.0,
"RightDownVectorBar": 580.0,
"RightUpDownVector": 580.0,
"RightUpTeeVector": 580.0,
"RightUpVector": 580.0,
"RightUpVectorBar": 580.0,
"ShortDownArrow": 580.0,
"ShortUpArrow": 580.0,
"UpArrow": 580.0,
"UpArrowBar": 580.0,
"UpArrowDownArrow": 580.0,
"UpDownArrow": 580.0,
"UpEquilibrium": 580.0,
"UpTeeArrow": 580.0,
"Power": 590.0,
"StringJoin": 600.0,
"Factorial": 610.0,
"Factorial2": 610.0,
"Apply": 620.0,
"Map": 620.0,
"Prefix": 640.0,
"Decrement": 660.0,
"Increment": 660.0,
"PreDecrement": 660.0,
"PreIncrement": 660.0,
"Unset": 670.0,
"Information": 670.0,
"GreaterSlantEqual": 670.0,
"LessSlantEqual": 670.0,
"Derivative": 670.0,
"MapApply": 670.0,
"PatternTest": 680.0,
"Get": 720.0,
"MessageName": 750.0,
}

SORTED_SYMBOLS_BY_PRECEDENCE = [
"CompoundExpression",
Expand Down Expand Up @@ -546,41 +322,8 @@
]


@pytest.mark.skipif(MATHICS_NOT_INSTALLED, reason="Requires Mathics-core installed")
@pytest.mark.parametrize(
(
"symbol",
"prec",
),
list(WMA_PRECEDENCES.items()),
)
@pytest.mark.xfail
def test_precedence_values(symbol, prec):
"""
TrueRelPrecedence[op1_, op2_] :=
Module[{formatted =
ToString[
HoldForm[ope2[ope1[a, b], c]] /. {ope1 -> op1, ope2 -> op2},
InputForm]},
Not[Or[StringPart[formatted, 1] == "(",
StringPart[formatted, -1] == ")"]]]
Transpose[{a, ALLOPS}] // TableForm"""

mathics_prec = session.evaluate(f"Precedence[{symbol}]").value
print("Check", f"Precedence[{symbol}]=={prec}")
check_evaluation(
f"Precedence[{symbol}]=={prec}",
"True",
to_string_expr=True,
to_string_expected=True,
hold_expected=True,
failure_message=f"Precendece of {symbol} in mathics {mathics_prec} != WMA value {prec}",
expected_messages=None,
)


# TODO: rewrite this test by reading the table directly.
@pytest.mark.skipif(MATHICS_NOT_INSTALLED, reason="Requires Mathics-core installed")
def test_precedence_order():
"""
Expand Down

0 comments on commit 46694ea

Please sign in to comment.