9
$\begingroup$

Functions like Piecewise have cool, easy-to-read formatting. In the same vein, I think it would be wonderful if the Which function automatically returned output in a column or tabulated form:

 Which[a < b,     1,
       c < d,     2, 
       True,      3]

rather than the what currently happens, which can sometimes be difficult to read.

Which[a < b, 1, c < d, 2, True, 3]

This example happens to be easy to read, but for Which expressions with a large number of <condition, value> pairs, it would be nice to have a structured layout for the output.

Any suggestions as to how to make this happen automatically?

$\endgroup$

2 Answers 2

14
$\begingroup$

$Post is handy but it can get confusing when you want to use it for many things at once.

I propose using MakeBoxes for this kind of thing as it is specifically intended for specifying formatted (Box) output.

Interpretation is used to make the output work correctly as input.

The right-hand-side of the definition can be either explicit *Box expressions or you can use ToBoxes to convert "normal" expressions to box form.

MakeBoxes[p : Which[x__], fmt_] := 
 Interpretation[
   Row @ {Which, MatrixForm @ Partition[Defer /@ Unevaluated[{x}], 2]},
   p
 ] ~ToBoxes~ fmt

Which[a < b, 1, c < d, 2, True, 3]

enter image description here

Alternatively with square brackets:

MakeBoxes[p : Which[x__], fmt_] := 
 Interpretation[
   Style[HoldForm[Which][Grid @ Partition[List @@ Defer /@ Hold[x], 2]], SpanMaxSize -> ∞],
   p
 ] ~ToBoxes~ fmt

Which[a < b, Print@1, c < d, Print@2, True, Print@3]

enter image description here

(Incidentally List @@ Defer /@ Hold[x] and Defer /@ Unevaluated[{x}] are two ways to do the same thing; take your pick for which is easier to read.)

$\endgroup$
2
  • $\begingroup$ Very cool - especially the square bracket version. One wonders why this is not built-in to Mma? ... at least for 30 rows or less. $\endgroup$
    – wolfies
    Commented Jul 20, 2013 at 19:54
  • $\begingroup$ @Rojo Please let me know if you see any other/new problems with my current code. $\endgroup$
    – Mr.Wizard
    Commented Jul 21, 2013 at 2:19
8
$\begingroup$

When I want to modify an output then first thing that comes to mind is $Post.

$Post = If[Head[#] === Which, 
                             Row[{Which, MatrixForm@Partition[List @@ #, 2]}],
                             #] &;

Which[a < b, 1, c < d, 2, True, 3]

enter image description here

Moreover, there is nothing to prevent you from using the 2D input interface with Which. You only have to be aware what you are writing.

So using standard Crtl+, with Crtl+Enter you can write like this:

enter image description here

And, if you haven't reset $Post=. from what I showed above, the output will be:

enter image description here

$\endgroup$
2
  • $\begingroup$ Wow Kuba, $Post is great stuff :). This is no ordinary plotting ;). $\endgroup$ Commented Jul 19, 2013 at 23:25
  • $\begingroup$ @JacobAkkerboom Quite interesting, but I suspect it is going to make some troubles when overdosed :) First faced here $\endgroup$
    – Kuba
    Commented Jul 19, 2013 at 23:33

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.