HOWTO: Call Matlab from Java {Kinda}

Looking over some of the reports on my blog reveal that pretty much everyone to this point looking at this blog look at the Java / Matlab post and not much else. Therefore, here’s everything I’ve learned concretely on how to call Matlab from Java and what NOT to do to save you some grief:

What I did:
Make a file that contains all the commands you want to run when MATLAB starts. My script file looks like this (named scriptName):

cd /directoryWithMATLABScript/
myMATLABScript
quit

The Java code I have used is a modified version of the code here. Now, use the following Java code to call MATLAB with the commands from your script:

UPDATE (07/25): Appending to the output and error Strings in the method provided is ok for MATLAB scripts with small amounts of output. On scripts that produce large amounts of output, constantly reallocating memory to new Strings and copying over the old contents of output takes an unnecessarily long amount of time. Use a StringBuffer and its append method instead.

public static String runScript(File scriptName) {
String output = “”, error = “”;
try {
String commandToRun = “/Applications/MATLAB73/bin/matlab -nodisplay < ” + scriptName;
System.out.println(commandToRun);
Process p = Runtime.getRuntime().exec(commandToRun);

String s;

BufferedReader stdInput = new BufferedReader(new
InputStreamReader(p.getInputStream()));

BufferedReader stdError = new BufferedReader(new
InputStreamReader(p.getErrorStream()));

// read the output from the command
System.out.println(“\nHere is the standard output of the command:\n”);
while ((s = stdInput.readLine()) != null) {
output += s + “\n”;
System.out.println(s);
}

// read any errors from the attempted command
System.out.println(“\nHere is the standard error of the command (if any):\n”);
while ((s = stdError.readLine()) != null) {
error += s + “\n”;
System.out.println(s);
}

} catch (Exception e) {
System.out.println(“exception happened – here’s what I know: “);
e.printStackTrace();
System.exit(-1);
}
return output + error;
}

This method will run MATLAB, pipe in the commands from the script file, and capture the standard output and standard error into Strings, and return that. Feel free to modify this code to play with the output or errors you’re getting from MATLAB. You can also use a DataOutputStream to push data back into MATLAB; if you’re interested in that, this link pretty much summarizes it up (third post down).

It is important to use the “-nodisplay” flag when calling MATLAB, otherwise the MATLAB GUI / IDE will open and the contents of the script won’t be called. Be sure to read about the caveats of this method below! If this was helpful, drop a comment off and let me know!

What NOT to DO / Things to keep in mind:

  1. The Matlab site gives an example of using the JAR that comes with the Matlab installation to call Java from Matlab. This requires you to start up MATLAB first, then call your Java program from it, which is the exact OPPOSITE of what you need to do. Furthermore, there is ZERO documentation on this JAR, so if there was a way to do it, nobody seems to know (at least based from multiple Google searches).
  2. The Java documentation on the Process class gives many warnings about what types of programs you should not make it call. Make sure your MATLAB program is not one of them or you may get unreliable results.
  3. I had to remove all user interaction from my MATLAB scripts to get my code “functional”, but if you fiddle with the Output and Input Streams, you may be able to work around this.
  4. You COULD just have the Runtime method execute “matlab -r matlabScriptName” and it will start up MATLAB and run “matlabScriptName.m”, but once it’s done it will idle and never quit. Technically this works, but you’ll need a way to kill the MATLAB process cleanly, as hoping Java will do it for you orphans some of MATLAB’s helper programs.
  5. Newer versions of MATLAB come bundled with a Matlab to C compiler appropriately called “MCC”, located in the “bin” directory of your MATLAB installation. You COULD use it to compile Matlab code into C code and then just run the C code from Java, but it’s not supported on Mac OS X, so it doesn’t work for me, and Google searches on the net show that many others have had problems with it. Furthermore, it doesn’t look like it pulls in the needed dependencies for all your files, so it’s not obvious if it’ll work as a standalone file. Spending several hours trying to fix the MCC so that it would work on Mac OS X proved futile, as there ended up being other problems with the C linker…

Hopefully this saves any of you some of the time it took me figuring this out.

19 Responses to “HOWTO: Call Matlab from Java {Kinda}”

  1. Calling Matlab from Java: Now 20% Less Painful! « The Wanderer Says:

    [...] Calling Matlab from Java: Now 20% Less Painful! UPDATE: The follow-up to this article can be found here. [...]

  2. Antonio Says:

    Hi, this how-to is very interesting!!I have a problem…How can I pass the script parameters (if script has of them)?

    THANKS!!

  3. shatterednirvana Says:

    You should be able to put them on the same line, so if your function is sin and it takes one argument, it should be sin x. So your script would be like:

    cd /tmp
    sin 1
    quit

    Which would just print 0 since sin 1 = 0, but that is how to (generally speaking) do it.

  4. mj Says:

    Hi, it is nice article, but when I call matlab with “-nodisplay” flag the matlab GUI is loaded as same as without this option
    Forthermore option “matlab <” + file does not work that way the matlab is run with instruction saved in file but only matlab window is appearing.

    I tried call matlab functions with making startup.m file. and it works that way the matlab window is opened (even with -nodisplay) and the instructions are executed but there is no output from matlab sent to java.

    Could you help me? I use WinXP.

  5. shatterednirvana Says:

    Hmm, all I have is a Vista box and I’ve been having a miserable time trying to get MATLAB to work. Let me try to get it up and going and I’ll look into it.

  6. JEREMIE Says:

    Hi, good “HOWTO” you have written.

    Well, i have a problem with your script.
    I used this command :

    String commandToRun = “C:\\MATLAB6p5\\bin\\matlab -nodisplay < E:\\workspaceMatlab\\dans_poly.m”;

    And then i get this error :

    C:\MATLAB6p5\bin\matlab -nodisplay < E:\workspaceMatlab\dans_poly.m
    exception happened – here’s what I know:
    java.io.IOException: Cannot run program “C:\MATLAB6p5\bin\matlab”: CreateProcess error=2, Sistem can’t find the specified file
    at java.lang.ProcessBuilder.start(ProcessBuilder.java:459)
    at java.lang.Runtime.exec(Runtime.java:593)

    Could you help me to correct this ? I use NetBeans 5.5 on WinXP.

    Thanks.

  7. shatterednirvana Says:

    What’s the output of doing a “dir” on that directory (C:\MATLAB6p5\bin\matlab)? I still don’t have MATLAB up and going, so I can’t really try it out on my box, unfortunately. The input redirection symbol “<” may also work differently on Windows, which would explain your problem and mj’s problem (see three comments ago).

  8. Timothy Wall Says:

    These guys are working on an alternative that gives you the equivalent of the C API for MATLAB in Java. Actual implementation time for this approach is about a day, which includes exhaustive testing:

    https://jna.dev.java.net/servlets/BrowseList?list=users&by=thread&from=935824

    BTW, this solution is also cross-platform.

  9. shatterednirvana Says:

    Wow, that looks like a great solution Timothy! Thanks for the link!

  10. zahir Says:

    Hi, good “HOWTO” you have written.
    Well, i have a problem with your script.
    I used this command :
    String commandToRun = “C:\\Program Files\\MATLAB\\R2007a\\bin\\matlab.bat -nodisplay < C:\\Haar Transform\\myscript.txt”;
    And i dont get any error but the matlab myscripts do’nt get executed . on succesfull execution an image is Should be written in the output folder.
    Could you help me to correct this ? I use NetBeans 5.5 on WinXP.
    Thanks.

  11. tiago Says:

    Hi,
    Actually it’s really easy to make matlab quir if using matlab – r.
    Just add the exit command at the end of the command-line.
    Eg: matlab -r version;exit
    Bye

  12. harry Says:

    Hi,
    from what I’ve seen (and tried), using pipes doesn’t work on Windows.

    See: http://www.mathworks.com/matlabcentral/newsreader/view_thread/171255#438689

  13. joshuadf Says:

    An alternative to Java’s built-in Runtime.exec() are the taskdefs used by ant. This gives you full threaded i/o and the ability to kill off the matlab process after a time limit if you want. I put up a trivial example called antExecute.java that you can easily find by searching the web (sorry, no direct link so this comment won’t be discarded as spam).

  14. nicholasv Says:

    If my problem is such that I have to call
    Process p = Runtime.getRuntime().exec(commandToRun);
    again and again ( like doing some processing again based on previous processing and thus changing the matlab script file each time ), it opens command window for every call and it takes significant time. Is there are a workaround for this problem?

  15. Moon14 Says:

    how to make script file

  16. stupent - students @ work Says:

    Accessing Matlab from Java…

    Today i had to access a matlab script from a java program. After some hours of trying to get it work by using matlabs command line i found a method to call a matlab script without using the command line. Using matlab -r “functionName” didn….

  17. Loociano Says:

    Hi, I also get a problem when I make the program run. How should be the script created? The direction with the -nodisplay flag changes also with the Matlab version?

    I’m using Netbeans in Win Vista and Matlab 2007b

    Thanks

  18. MOh Says:

    Hi,
    my project is due very soon..I desperately need some help…I can run matlab function from another program(say java or shellscript)…but how can I pass argument ..for example in shellscript I can run matlab < testprog, and it runs fine..however I cannot run with argument say testprog(1,1) etc..
    Any help will be really appreciated….
    thanks

  19. raghav Says:

    hiii…
    i want a help……i want to send a image from java to matlab n then in matalb i want to compare two images and bring back result to java as true if images are equal and false if not equals….plz help me out ….what to do…how to send images n bring back…

Leave a Reply