Mutare.Mutators.OperandSwap (mutare v0.1.1)

Copy Markdown View Source

Reverses the first two operands of non-commutative operators and calls.

Operators

  • -, /, and **
  • <>
  • ++ and --
  • div, rem — integer division / remainder.

The operator is retained; only the operands are exchanged.

The following operators are excluded:

  • >, >=, <, and <=, because Mutare.Mutators.Relational already produces the equivalent direction change
  • commutative operators such as +, *, equality, and boolean operators
  • in, because the swapped right operand may not be enumerable
  • = and |>, whose operands have different roles

Calls

The first two arguments are exchanged in these calls:

A trailing unit in diff/3 is retained and may be mutated separately by Mutare.Mutators.ModeSwap.

Aliased and imported calls are supported. An alias that resolves to another module does not match.

Piped calls

A piped stage supplies its effective first operand from the pipe, so it is not present in the call node. The transpose is still produced by wrapping the swapped call in a one-argument capture invoked on the piped value, which routes that value into the second position:

foo |> Kernel.++(bar)    foo |> (&Kernel.++(bar, &1)).()

This covers the operator forms (Kernel.++, Kernel.-, Kernel.<>, …), Kernel.div/rem, and the remote calls above. A bare Kernel call (a |> div(b)) is not resolved and stays untouched.

Skipped cases

Identical operands are not swapped (in direct calls — a piped stage cannot see its piped operand, so an identical-operand pipe yields an equivalent transpose). Unary minus has no second operand and is handled by Mutare.Mutators.Arithmetic.

Guard-safe operators and calls are also mutated in guards.