Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- (****** ToMatlab.mth -- Mathematica expressions into Matlab form *************)
- (*
- ToMatlab[expr]
- Converts the expression expr into matlab syntax and
- returns it as a String.
- ToMatlab[expr, name]
- Returns an assignment of expr into name as a String. name can be also
- a more complicated string, e.g.,
- ToMatlab[If[t,a,b],"function y=iffun(t,a,b)\ny"].
- The special symbol Colon can be used to denote the matlab colon
- operator :, and Colon[a,b] for a:b, Colon[a,b,c] for a:b:c.
- WriteMatlab[expr, file]
- WriteMatlab[expr, file, name]
- Writes the expr in matlab form into the given file. The second form
- makes this an assignment into the variable name. Example:
- f = OpenWrite["file.m"];
- WriteMatlab[Cos[x]-x, f, y];
- Close[f];
- The file argument can also be a String that gives the name of the
- file:
- WriteMatlab[Cos[x]-x, "file.m", y];
- achieves the same result as the previous example (but this limits one
- expression per file).
- PrintMatlab[expr]
- PrintMatlab[expr, name]
- is like ToMatlab but instead of returning the String, it is printed on
- the screen.
- RulesToMatlab[rules]
- Where rules is the result from Solve or NSolve: converts the rules into
- individual assignment statements.
- *)
- (* (C) 1997-1999 Harri Ojanen
- harri.ojanen@iki.fi
- http://www.iki.fi/~harri.ojanen/ *)
- (*
- Last modified June 15 2011 by Eric Cousineau
- eacousineau@gmail.com
- Fixed a bug concerning vertcat errors in Matlab due to binary/unary operators in Matlab and the Dot-Dot-Dot operator
- *)
- BeginPackage["MatlabUtils`ToMatlab`"]
- ToMatlab::usage =
- "ToMatlab[expr] converts the expression expr into matlab syntax and returns it as a String.\nToMatlab[expr, name] returns an assignment of expr into name as a String. name can be also a more complicated string, e.g., ToMatlab[If[t,a,b],\"function y=iffun(t,a,b)\\ny\"].\nThe special symbol Colon can be used to denote the matlab colon operator :, and Colon[a,b] for a:b, Colon[a,b,c] for a:b:c.\nSee also WriteMatlab and PrintMatlab.\nAll functions accept an optional last argument that is the maximum line width."
- WriteMatlab::usage =
- "WriteMatlab[expr, file] or WriteMatlab[expr, file, name] Writes the expr in matlab form into the given file. The second form makes this an assignment into the variable name.\nExample: f = OpenWrite[\"file.m\"]; WriteMatlab[Cos[x]-x, f, y]; Close[f];\nThe file argument can also be a String that gives the name of the file: WriteMatlab[Cos[x]-x, \"file.m\", y]; achieves the same result as the previous example (but this limits one expression per file).\nSee also ToMatlab and PrintMatlab."
- PrintMatlab::usage =
- "PrintMatlab[expr] or PrintMatlab[expr, name] is like ToMatlab but instead of returning the String, it is printed on the screen. See also ToMatlab and WriteMatlab."
- RulesToMatlab::usage =
- "RulesToMatlab[rules] where rules is from Solve or NSolve converts the rules into individual assignment statements."
- (*SetMargin::usage = "SetMargin[margin]"
- RestoreMargin::usage = "RestoreMargin[]"*)
- Begin["`Private`"]
- WriteMatlab[e_, file_OutputStream] :=
- (WriteString[file, ToMatlab[e,72]];)
- WriteMatlab[e_, file_OutputStream, name_] :=
- (WriteString[file, ToMatlab[e,name,72]];) /; (!NumberQ[name])
- WriteMatlab[e_, file_String] :=
- (Block[{f = OpenWrite[file]},
- WriteString[f, ToMatlab[e,72]];
- Close[f];];)
- WriteMatlab[e_, file_String, name_] :=
- (Block[{f = OpenWrite[file]},
- WriteString[f, ToMatlab[e,name,72]];
- Close[f];];) /; (!NumberQ[name])
- WriteMatlab[e_, file_OutputStream, margin_Integer] :=
- (WriteString[file, ToMatlab[e,margin]];)
- WriteMatlab[e_, file_OutputStream, name_, margin_Integer] :=
- (WriteString[file, ToMatlab[e,name,margin]];)
- WriteMatlab[e_, file_String, margin_Integer] :=
- (Block[{f = OpenWrite[file]},
- WriteString[f, ToMatlab[e,margin]];
- Close[f];];)
- WriteMatlab[e_, file_String, name_, margin_Integer] :=
- (Block[{f = OpenWrite[file]},
- WriteString[f, ToMatlab[e,name,margin]];
- Close[f];];)
- PrintMatlab[e_] :=
- (Print[ToMatlab[e, 60]];)
- PrintMatlab[e_, name_] :=
- (Print[ToMatlab[e, name, 60]];) /; (!NumberQ[name])
- PrintMatlab[e_, margin_Integer] :=
- (Print[ToMatlab[e, margin]];)
- PrintMatlab[e_, name_, margin_Integer] :=
- (Print[ToMatlab[e, name, margin]];)
- ToMatlab[e_] := foldlines[ToMatlabaux[e] <> ";\n"]
- ToMatlab[e_, name_] :=
- ToMatlabaux[name] <> "=" <> foldlines[ToMatlabaux[e] <> ";\n"] /;
- (!NumberQ[name])
- ToMatlab[e_, margin_Integer] :=
- Block[{s},
- SetMargin[margin];
- s = foldlines[ToMatlabaux[e] <> ";\n"];
- RestoreMargin[];
- s]
- ToMatlab[e_, name_, margin_Integer] :=
- Block[{s},
- SetMargin[margin];
- s = ToMatlabaux[name] <> "=" <> foldlines[ToMatlabaux[e] <> ";\n"];
- RestoreMargin[];
- s]
- RulesToMatlab[l_List] :=
- If[Length[l] === 0,
- "",
- Block[{s = RulesToMatlab[ l[[1]] ]},
- Do[s = s <> RulesToMatlab[ l[[i]] ], {i, 2, Length[l]}];
- s]]
- RulesToMatlab[Rule[x_, a_]]:=
- ToMatlab[a, ToMatlab[x] // StringDrop[#, -2]&]
- (*** Numbers and strings *****************************************************)
- ToMatlabaux[s_String] := s
- ToMatlabaux[n_Integer] :=
- If[n >= 0, ToString[n], "(" <> ToString[n] <> ")"]
- (*ToMatlabaux[r_Rational] :=
- "(" <> ToMatlabaux[Numerator[r]] <> "/" <>
- ToMatlabaux[Denominator[r]] <> ")"*)
- ToMatlabaux[r_Rational] :=
- "(" <> ToString[Numerator[r]] <> " / " <>
- ToString[Denominator[r]] <> ")"
- ToMatlabaux[r_Real] :=
- Block[{a = MantissaExponent[r]},
- If[r >= 0,
- ToString[N[a[[1]],18]] <> "e" <> ToString[a[[2]]],
- "(" <> ToString[N[a[[1]],18]] <> "e" <> ToString[a[[2]]] <> ")"]]
- ToMatlabaux[I] := "sqrt(-1)";
- ToMatlabaux[c_Complex] :=
- "(" <>
- If[Re[c] === 0,
- "",
- ToMatlabaux[Re[c]] <> " + "] <>
- If[Im[c] === 1,
- "sqrt(-1)",
- "sqrt(-1) * " <> ToMatlabaux[Im[c]] ] <> ")"
- (*** Lists, vectors and matrices *********************************************)
- numberMatrixQ[m_] := MatrixQ[m] && (And @@ Map[numberListQ,m])
- numberListQ[l_] := ListQ[l] && (And @@ Map[NumberQ,l])
- numbermatrixToMatlab[m_] :=
- Block[{i, s=""},
- For[i=1, i<=Length[m], i++,
- s = s <> numbermatrixrow[m[[i]]];
- If[i < Length[m], s = s <> ";"]];
- s]
- numbermatrixrow[l_] :=
- Block[{i, s=""},
- For[i=1, i<=Length[l], i++,
- s = s <> ToMatlabaux[l[[i]]];
- If[i < Length[l], s = s <> ", "]];
- s]
- ToMatlabaux[l_List /; MatrixQ[l]] :=
- If[numberMatrixQ[l],
- "[" <> numbermatrixToMatlab[l] <> "]",
- "[" <> matrixToMatlab[l] <> "]"]
- matrixToMatlab[m_] :=
- If[Length[m] === 1,
- ToMatlabargs[m[[1]]],
- ToMatlabargs[m[[1]]] <> ";" <>
- matrixToMatlab[ argslistdrop[m] ] ]
- ToMatlabaux[l_List] := "[" <> ToMatlabargs[l] <> "]"
- (*** Symbols *****************************************************************)
- ToMatlabaux[Colon] = ":"
- ToMatlabaux[Abs] = "abs"
- ToMatlabaux[Min] = "min"
- ToMatlabaux[Max] = "max"
- ToMatlabaux[Sin] = "sin"
- ToMatlabaux[Cos] = "cos"
- ToMatlabaux[Tan] = "tan"
- ToMatlabaux[Cot] = "cot"
- ToMatlabaux[Csc] = "csc"
- ToMatlabaux[Sec] = "sec"
- ToMatlabaux[ArcSin] = "asin"
- ToMatlabaux[ArcCos] = "acos"
- ToMatlabaux[ArcTan] = "atan"
- ToMatlabaux[ArcCot] = "acot"
- ToMatlabaux[ArcCsc] = "acsc"
- ToMatlabaux[ArcSec] = "asec"
- ToMatlabaux[Sinh] := "sinh"
- ToMatlabaux[Cosh] := "cosh"
- ToMatlabaux[Tanh] := "tanh"
- ToMatlabaux[Coth] := "coth"
- ToMatlabaux[Csch] := "csch"
- ToMatlabaux[Sech] := "sech"
- ToMatlabaux[ArcSinh] := "asinh"
- ToMatlabaux[ArcCosh] := "acosh"
- ToMatlabaux[ArcTanh] := "atanh"
- ToMatlabaux[ArcCoth] := "acoth"
- ToMatlabaux[ArcCsch] := "acsch"
- ToMatlabaux[ArcSech] := "asech"
- ToMatlabaux[Log] := "log"
- ToMatlabaux[Exp] := "exp"
- ToMatlabaux[MatrixExp] := "expm"
- ToMatlabaux[Pi] := "pi"
- ToMatlabaux[E] := "exp(1)"
- ToMatlabaux[True] := "true"
- ToMatlabaux[False] := "false"
- ToMatlabaux[e_Symbol] := ToString[e]
- (*** Relational operators ****************************************************)
- ToMatlabaux[e_ /; Head[e] === Equal] :=
- ToMatlabrelop[ argslist[e], "=="]
- ToMatlabaux[e_ /; Head[e] === Unequal] :=
- ToMatlabrelop[ argslist[e], "~="]
- ToMatlabaux[e_ /; Head[e] === Less] :=
- ToMatlabrelop[ argslist[e], "<"]
- ToMatlabaux[e_ /; Head[e] === Greater] :=
- ToMatlabrelop[ argslist[e], ">"]
- ToMatlabaux[e_ /; Head[e] === LessEqual] :=
- ToMatlabrelop[ argslist[e], "<="]
- ToMatlabaux[e_ /; Head[e] === GreaterEqual] :=
- ToMatlabrelop[ argslist[e], ">="]
- ToMatlabaux[e_ /; Head[e] === And] :=
- ToMatlabrelop[ argslist[e], "&"]
- ToMatlabaux[e_ /; Head[e] === Or] :=
- ToMatlabrelop[ argslist[e], "|"]
- ToMatlabaux[e_ /; Head[e] === Not] :=
- "~(" <> ToMatlabaux[e[[1]]] <> ")"
- ToMatlabrelop[e_, o_] :=
- If[Length[e] === 1,
- "(" <> ToMatlabaux[e[[1]]] <> ")",
- "(" <> ToMatlabaux[e[[1]]] <> ") " <> o <> " " <>
- ToMatlabrelop[ argslistdrop[e], o] ]
- relopQ[e_] := MemberQ[{Equal, Unequal, Less, Greater, LessEqual,
- GreaterEqual, And, Or, Not}, Head[e]]
- (*** Addition, multiplication and powers *************************************)
- ToMatlabaux[e_ /; Head[e] === Plus] :=
- If[relopQ[e[[1]]],
- "(" <> ToMatlabaux[e[[1]]] <> ")",
- ToMatlabaux[e[[1]]] ] <>
- " + " <>
- If[Length[e] === 2,
- If[relopQ[e[[2]]],
- "(" <> ToMatlabaux[e[[2]]] <> ")",
- ToMatlabaux[e[[2]]] ],
- ToMatlabaux[ dropfirst[e] ]]
- ToMatlabaux[e_ /; Head[e] === Times] :=
- If[Head[e[[1]]] === Plus,
- "(" <> ToMatlabaux[e[[1]]] <> ")",
- ToMatlabaux[e[[1]]] ] <>
- " .* " <>
- If[Length[e] === 2,
- If[Head[e[[2]]] === Plus,
- "(" <> ToMatlabaux[e[[2]]] <> ")",
- ToMatlabaux[e[[2]]] ],
- ToMatlabaux[ dropfirst[e] ]]
- ToMatlabaux[e_ /; Head[e] === Power] :=
- If[Head[e[[1]]] === Plus || Head[e[[1]]] === Times || Head[e[[1]]] === Power,
- "(" <> ToMatlabaux[e[[1]]] <> ")",
- ToMatlabaux[e[[1]]] ] <>
- " .^ " <>
- If[Length[e] === 2,
- If[Head[e[[2]]] === Plus || Head[e[[2]]] === Times || Head[e[[2]]] === Power,
- "(" <> ToMatlabaux[e[[2]]] <> ")",
- ToMatlabaux[e[[2]]] ],
- ToMatlabaux[ dropfirst[e] ]]
- (*** Special cases of functions **********************************************)
- ToMatlabaux[Rule[_,r_]] := ToMatlabaux[r]
- ToMatlabaux[Log[10, z_]] := "log10(" <> ToMatlabaux[z] <> ")"
- ToMatlabaux[Log[b_, z_]] :=
- "log(" <> ToMatlabaux[z] <> ") ./ log(" <> ToMatlabaux[b] <> ")"
- ToMatlabaux[Power[e_, 1/2]] := "sqrt(" <> ToMatlabaux[e] <> ")"
- ToMatlabaux[Power[E, z_]] := "exp(" <> ToMatlabaux[z] <> ")"
- ToMatlabaux[If[test_, t_, f_]] :=
- Block[{teststr = ToMatlabaux[test]},
- "((" <> teststr <> ") .* (" <> ToMatlabaux[t] <> ") + (~("
- <> teststr <> ")) .* (" <> ToMatlabaux[f] <> "))"]
- ToMatlabaux[e__ /; (Head[e] === Max || Head[e] == Min)] :=
- ToMatlabaux[Head[e]] <> "(" <>
- If[ Length[e] === 2,
- ToMatlabargs[e] <> ")",
- ToMatlabaux[e[[1]]] <> ", " <> ToMatlabaux[dropfirst[e]] <> ")"]
- ToMatlabaux[Colon[a_,b_]] :=
- "((" <> ToMatlabaux[a] <> "):(" <> ToMatlabaux[b] <> "))"
- (*Is this correct? *)
- ToMatlabaux[Colon[a_,b_,c_]] :=
- "((" <> ToMatlabaux[a] <> "):(" <> ToMatlabaux[b] <>
- "):(" <> ToMatlabaux[c] <> "))"
- (*** General functions *******************************************************)
- ToMatlabaux[e_] :=
- ToMatlabaux[Head[e]] <> "(" <>
- ToMatlabargs[ argslist[e] ] <> ")"
- ToMatlabargs[e_] :=
- If[Length[e] === 1,
- ToMatlabaux[e[[1]]],
- ToMatlabaux[e[[1]]] <> "," <>
- ToMatlabargs[ argslistdrop[e] ] ]
- (*** Argument lists **********************************************************)
- (*** argslist returns a List of the arguments ***)
- argslist[e_] :=
- Block[{ARGSLISTINDEX}, Table[ e[[ARGSLISTINDEX]],
- {ARGSLISTINDEX, 1, Length[e]}]]
- (*** argslistdrop returns a List of all arguments except the first one ***)
- argslistdrop[e_] :=
- Block[{ARGSLISTINDEX}, Table[ e[[ARGSLISTINDEX]],
- {ARGSLISTINDEX, 2, Length[e]}]]
- (*** dropfirst is like argslistdrop but retains the original Head ***)
- dropfirst[e_] :=
- e[[ Block[{i}, Table[i, {i,2,Length[e]}]] ]]
- (*** Folding long lines ******************************************************)
- MARGIN = 66
- MARGINS = {}
- SetMargin[m_] := (MARGINS = Prepend[MARGINS, MARGIN]; MARGIN = m; MARGINS)
- RestoreMargin[] :=
- If[Length[MARGINS] > 0,
- MARGIN = MARGINS[[1]];
- MARGINS = Drop[MARGINS, 1]]
- foldlines[s_String] :=
- Block[{cut, sin=s, sout=""},
- While[StringLength[sin] >= MARGIN,
- cut = findcut[sin];
- If[cut > 0,
- sout = sout <> StringTake[sin,cut] <> " ...\n ";
- sin = StringDrop[sin,cut],
- (* else *)
- sout = sout <> StringTake[sin,MARGIN];
- sin = StringDrop[sin,MARGIN]]];
- sout <> sin]
- findcut[s_String] :=
- Block[{i=MARGIN},
- While[i > 0 &&
- !MemberQ[{";", ",", "(", ")", "+", "*", " "}, StringTake[s,{i}]],
- i--];
- i]
- End[]
- EndPackage[]
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement