views:

1611

answers:

3

If you have Mathematica code in foo.m, Mathematica can be invoked with -noprompt and with -initfile foo.m (or -run "<<foo.m") and the command line arguments are available in $CommandLine (with extra junk in there) but is there a way to just have some mathematica code like

#!/usr/bin/env MathKernel
x = 2+2;
Print[x];
Print["There were ", Length[ARGV], " args passed in on the command line."];
linesFromStdin = readList[];
etc.

and chmod it executable and run it? In other words, how does one use Mathematica like any other scripting language (Perl, Python, Ruby, etc)?

+2  A: 

Try
-initfile filename
And put the exit command into your program

Lev
Thanks, that's an improvement over -run. I updated the question. I have what I think is a more complete solution that I'll post shortly.
dreeves
In my mash.pl solution it turns out you do have to use -run, not -initfile. I'm not sure why but the latter causes problems with mathematica scripts that read from files.
dreeves
+3  A: 

MASH -- Mathematica Scripting Hack -- will do this.

Since Mathematica version 6, the following perl script suffices:

http://ai.eecs.umich.edu/people/dreeves/mash/mash.pl

For previous Mathematica versions, a C program is needed:

http://ai.eecs.umich.edu/people/dreeves/mash/pre6

dreeves
+1  A: 

Here is a solution that does not require an additional helper script. You can use the following shebang to directly invoke the Mathematica kernel:

#!/bin/sh
exec <"$0" || exit; read; read; exec /usr/local/bin/math -noprompt "$@" | sed '/^$/d'; exit
(* Mathematica code starts here *)
x = 2+2;
Print[x];

The shebang code skips the first two lines of the script and feeds the rest to the Mathematica kernel as standard input. The sed command drops empty lines produced by the kernel.

This hack is not as versatile as MASH. Because the Mathematica code is read from stdin you cannot use stdin for user input, i.e., the functions Input and InputString do not work.

sakra
Nice! Thanks, sakra!
dreeves