# Defining conditional Notation rules

I am trying to define a notation rule so that for selected symbols subsripts will be equivalent to function parameters. My understanding of the docs suggests the following

<< Notation

sub[f_] := Notation[ParsedBoxWrapper[$$Subscript[\(f, \(\ x_$$\)]\)]
\[DoubleLongLeftRightArrow] ParsedBoxWrapper[$$f[x_]$$]]


The idea is to be able to do the following

sub[P]
Subscript[P, i] := F[i]
Subscript[P, a]


and have Mathematica treat it the same as

P[i] := F[i]
P[a]


But Subscript[Q, i] should remain as a just a subscript expression

Mathematica throws the following error on the definition of sub:

Notation::expatnf: Pattern 'x' appearing in the external representation 'NotationPrivateidentityForm[RowBox[{OverBar,[,x_,]}]]' cannot be filled since 'x' does not appear in the internal representation 'NotationPrivateidentityForm[RowBox[{mean,[,x,]}]]'. >>


I would like to understand what the problem is and fix it. I am also interest in alternative approaches to achieving the same effect. I am also interested finding more documantation for the Notation package then is in the standard documentation, particularly extended examples and conceptual overviews.

** EDIT

Here is what I get with Leonid's approach

In:=
Remove[P, F]
Clear[Subscript, MakeExpression, makeExpression];
MakeExpression[expr_, form_] :=
With[{result = makeExpression[expr, form]},
ClearAll[sub];
sub[f_] := With[{boxed = MakeBoxes[f]},
makeExpression[RowBox[{"Subscript", "[",
RowBox[{boxed, ",", arg_}], "]"}], form_] :=
MakeExpression[RowBox[{boxed, "[", arg, "]"}], form]];

In:= sub[P]

In:= Subscript[P, i]:= F[i]


I would really prefer the rule to be interpreted as P[i] := F[i]. I want the subscripts to be purely cosmetic. On my system the Subscript[P, i] on the LHS does not get interpreted that way:

In:= DownValues[Subscript]

Out= {HoldPattern[Subscript[P, i]] :> F[i]}

In:= DownValues[P]

Out= {}


The following shows that the parsing of the notation works, but I actually want the rendering to reverse the parsing when in StandardForm.

In:= Subscript[P, a]

Out= P[a]


However the := definition does not work as kick in:

In:= Subscript[P, i]

Out= P[i]


Also the parsing code only works on code that was entered after the notation related code was evaluated. Expressions entered before the notation code was evaluated are not effected, even after restarting Mathematica. The following expression is in the same notebook but was in there from before Leonids answer and is identical to the first expression above:

In:= Subscript[P, a]

Out= Subscript[P, a]


In other words the notebook is somehow remembering which expressions were entered before the notation code and which were entered after even across Mathematica restarts.

One of the problems of the Notation package is that it is rather heavy and opaque, while what it actually does is rather simple. I suggest a very light-weight substitute for your case:

Clear[MakeExpression,makeExpression];
MakeExpression[expr_,form_]:=
With[{result=makeExpression[expr,form]},
];

ClearAll[sub];
sub[f_]:=
With[{boxed=MakeBoxes[f]},
makeExpression[
RowBox[{"Subscript","[",RowBox[{boxed,",",arg_}],"]"}],form_
]:=
MakeExpression[RowBox[{boxed,"[",arg,"]"}],form];

makeExpression[SubscriptBox[boxed, arg_], form_] :=
MakeExpression[RowBox[{boxed, "[", arg, "]"}], form];
];


Now, you use this as you would in your question:

sub[P]
Subscript[P, i] := F[i]
Subscript[P, a]

(* P[a] *)

Subscript[P, i]

(* F[i] *)


while for a general subscript with a different symbol you get the same as before:

Subscript[Q, i]

(* Subscript[Q, i] *)

• Thanks. Where should I put the initial definitions. Simply adding them at the top of the notebook and evaluating the notebook does not seem to be doing this. – Daniel Mahler Apr 2 '14 at 18:44
• @DanielMahler Just tested once again on a fresh kernel, M9.0.0, Mac OS X, placed the definitions in a cell and evaluated in a newly created notebook. The test usage is in a different cell. Everything works fine for me. – Leonid Shifrin Apr 2 '14 at 18:52
• @All would be nice if those reading my answer above, could confirm whether or not this works for them, and on which platforms. – Leonid Shifrin Apr 2 '14 at 19:03
• Works on Win7/M9.0.1 – Ymareth Apr 2 '14 at 19:24
• @Ymareth Thanks for checking! – Leonid Shifrin Apr 2 '14 at 19:26

Here is how to fix up your sub definition to do what you want:

sub[f_Symbol] := With[{n = SymbolName[f]},
Notation[ParsedBoxWrapper @ SubscriptBox[n, "x_"] ⟺ ParsedBoxWrapper @ RowBox[{n, "[", "x_", "]"}]]
]


Clear[P]
Subscript[P, i_] := F[i]
P[a]


F[a]

The DownValues of P have been defined as desired:

DownValues[P] //InputForm


{HoldPattern[P[i_]] :> F[i]}