5

I did something silly I think.

I changed my cell style to 'code' and starting changing indentation and moving code around the way I like to, (since it is easier to do that in 'code' cell style, as the notebook interface does not get in the way). But after trying it for a while, I find other issues with this with this style.

Now I changed the style back to 'input'. But now all the code has all these extra spaces in them, and code does not look good any more as it was in the original 'input' style.

I made too many edits and manual formatting to the code.

Is there a way to tell Mathematica to 'auto-format' the code back to the default input style? i.e. remove all the extra space where needed, realign things the way they were, etc...

If I have to do this by hand, will take me forever. I could not find such as option. I tried many options there on the menues, and nothing helps.

ps. in Matlab, this is trivial to do, just select all code, then select 'smart-ident' from a menu, and it will do that.

ps. I tried emacs Mathematica mode, and they have no prety-print either.

EDIT

I tried these: Select cell, then Cell->Convert To, and selected 'InputForm' and also selected 'input Form Display'.

This seems to have removed all the extra white spaces. Which is good. Now I only need to go and just hit returns in all the right places to get it back to the original form.

At least this is much better than having to delete spaces by hand. So, disaster seems to be contained for now.

EDIT

screen shot after converting 'code' style back to 'standard form'. very hard to read.

enter image description here thanks,

EDIT

To make sure what the question is, given some Mathematica code, which is 'mangled' up, and formatted by hand with manual space inserting and manual inserting of returns all over, and now if I just put it in a notebook with default style, I want it to smart-indent back to the default setting, and have all the line-wrapping, etc... as if it was originally written in the default style. i.e. pretty-print to what it would be if it was written using the 'input' code style.

here is a small function as an example that I formatted by hand. It will look not well formatted even more when I paste it here. If you copy this code to your notebook, default style, then how to auto-format it back to the default settings without doing it by hand?

If[Abs@omega <= $MachineEpsilon,
    (
      data = {{0, 0}};
      p    = ListPlot[data, Sequence@plotOptions]
     ),
    (
      driverPeriod            = 2. Pi/Abs@omega;
      valuesOfDriverAmplitude = 
    Range[aStart, aStart + aLen, aLen/aIntervals];
      timeValues              = 
    Range[initialDriverPeriod*driverPeriod, 
     finalDriverPeriod*driverPeriod, driverPeriod ];

      data  = 
    Table[0, {Length[valuesOfDriverAmplitude]}, {Length[timeValues ]}];
      total = Length[timeValues]*Length[valuesOfDriverAmplitude];
      bifurcationProgress = 0.;
      count = 0.;

      Do[
         (
           {x1, x2, x3} = 
      solve[q, valuesOfDriverAmplitude [[i]], omega, phase, 
       initialDriverPeriod*driverPeriod,
                                (finalDriverPeriod)*driverPeriod, x10,
        x20, isDamped, 4, 4];
           currentTorqueAmplitude = valuesOfDriverAmplitude[[i]];
           Do[
              (

       data[[i, j]] = {currentTorqueAmplitude, x2[timeValues[[j]]  ]};
                count      += 1;
                bifurcationProgress = count/total;
               ),
                {j, 1, Length[timeValues]}
              ]
          ),
         {i, 1, Length[valuesOfDriverAmplitude]}
         ];

     p = ListPlot[Flatten[data, 1], Sequence@plotOptions]
     )
  ];

EDIT 6 PM

1) Saved the notebook as m file (mathematica package) called aclFix.m 2) then I did the following

str=Import["aclFix.m")

also tried

str=Get["aclFix.m"];

but in both cases, all what I get is the actual Manipulate on the screen showing up. And the command shown below (StringReplace etc....) does not work on it as it is not a string. I get lots of errors, such as

    StringReplace::strse: String or list of strings expected at position 1 in 
StringReplace[Manipulate[<<1>>,
{{aStart,0.9,},0,2,0.01,ImageSize->Tiny,ImagePadding->0,ControlPlacement->1},
{{aLen,0.2,},0.01,2,0.01,ImageSize->Tiny,ImagePadding->0,ControlPlacement->2},
<<45>>,SynchronousUpdating->False,ContinuousAction->False,<<6>>],
{(x_/;x==FromCharacterCode[32])..->,(x_/;x==<<17>>[9])..->}]. >>

may be I misunderstood the solution..

EDIT 1 AM

I exported the notebook as "m" file, Imported it back as

str = Import["aclFix.m", "Text"];

then

code=StringReplace[str, {(x_ /; x == FromCharacterCode[32]) .. -> 
   "", (x_ /; x == FromCharacterCode[9]) .. -> ""}]

then

Export["fix.m", code]

But it is still a string. When I import it back, it is still a string. I tried ToExpression[code] but it did nothing. How do convert it to actual code? This is an example looking at the .m using text editor. I used the above code to test it on. May be we are getting close here?

Will look more at it.

(* Created by Wolfram Mathematica 8.0 for Students - Personal Use Only : www.wolfram.com *)

"If[Abs@omega<=$MachineEpsilon,\n(\ndata={{0,0}};\np=ListPlot[data,Sequence@p\

lotOptions]\n),\n(\ndriverPeriod=2.Pi/Abs@omega;\nvaluesOfDriverAmplitude=\nR\

ange[aStart,aStart+aLen,aLen/aIntervals];\ntimeValues=\nRange[initialDriverPe\

riod*driverPeriod,\nfinalDriverPeriod*driverPeriod,driverPeriod];\n\ndata=\nT\

able[0,{Length[valuesOfDriverAmplitude]},{Length[timeValues]}];\ntotal=Length\

[timeValues]*Length[valuesOfDriverAmplitude];\nbifurcationProgress=0.;\ncount\

=0.;\n\nDo[\n(\n{x1,x2,x3}=\nsolve[q,valuesOfDriverAmplitude[[i]],omega,phase\

,\ninitialDriverPeriod*driverPeriod,\n(finalDriverPeriod)*driverPeriod,x10,\n\

x20,isDamped,4,4];\ncurrentTorqueAmplitude=valuesOfDriverAmplitude[[i]];\nDo[\

\n(\n\ndata[[i,j]]={currentTorqueAmplitude,x2[timeValues[[j]]]};\ncount+=1;\n\

bifurcationProgress=count/total;\n),\n{j,1,Length[timeValues]}\n]\n),\n{i,1,L\

ength[valuesOfDriverAmplitude]}\n];\n\np=ListPlot[Flatten[data,1],Sequence@pl\

otOptions]\n)\n];"
Nasser
  • 12,849
  • 6
  • 52
  • 104
  • Related question: [Mathematica code in email and keeping formatting the same as notebook](http://stackoverflow.com/q/6160043/421225) – Simon Sep 10 '11 at 04:11
  • @Nasser so, if you were to a) take all contiguous space characters and reduce them to a single character b) do nothing to the end-of-lines, would this do what you want? Because that could be done by a regex, which I guess I can provide (if nobody else does: hardly my area of expertise, but this looks simple enough) – acl Sep 10 '11 at 14:19
  • I don't have an answer to your specific question, but I will point out that the main differences between the Code style and the Input style are that the Code has the following settings: PageWidth->Infinity, AutoIndent->False, InitializationCell->True. If I want Code-style editing in an Input-style cell I often set PageWidth->Infinity, AutoIndent->False on that cell. – ragfield Sep 10 '11 at 21:29
  • @ACL, thanks, I just saw your comment. (hard to see new updated here since no threads to tell one where new item is). I am not sure how to do what you suggested. But all what I want, is to take some code, which was formated by hand, and have it auto-indented back as if it was written originally in the default 'input' cell style, with all the correct line wrapping etc.... I posted in an edit some function as an example. thanks. – Nasser Sep 11 '11 at 00:07
  • Nasser: In response to your "6 PM" edit: Mma will try to guess what you you mean when you call `Import["aclFix.m"]`. If you want to import explicitly as a [string](http://reference.wolfram.com/mathematica/ref/format/String.html), you have to tell it. Try `Import["aclFix.m", "String"]` or `Import["aclFix.m", "Text"]`. – Simon Sep 11 '11 at 07:20
  • @Simon, thanks, I did that. Now it 'works', but the result is not really working well. Please see edit. – Nasser Sep 11 '11 at 08:01
  • OK, I can see your edit now. Try taking the "fixed" string and running `ImportString[aclFixedString]` on it. Provided acl's method does not break the code, then it should just import like the original file. (by the way, removing spaces might not be good - `a x` != `ax`) – Simon Sep 11 '11 at 08:17
  • @Simon indeed, removing all spaces will break code. One can modify the replacement rule to simply convert all series of more than one spaces into a single space; but I am still trying to work out what the "broken" code looks like, and what the "fixed" code should look like. – acl Sep 11 '11 at 12:07
  • @acl: Yeah - I don't think that it's worth to spending too much time on it... – Simon Sep 11 '11 at 12:40

2 Answers2

5

It would be useful to have a sample of the code (not just visual). In the meantime, maybe this will work:

Save your code in an m-file. Then import it into the variable str, then run this

StringReplace[str,
 {
  (x_ /; x == FromCharacterCode[32]) .. -> "",
  (x_ /; x == FromCharacterCode[9]) .. -> ""
  }
 ]

and save the result into another m-file. What this does is to remove all series of one or more spaces or tabs. Thus, if for instance

str =
 "f[
    g[
        u   ]]"

(which contains both spaces and tabs) then running the code I gave gives

f[
g[
u]]

and you can save this back into an m-file.

If this doesn't do what you want then maybe if you provide a piece of code that is formatted the wrong way would help.

(or you could try with the interactive regexp-builder in emacs: m-x re-builder, but if you're not familiar with regexps it's probably not worth it)

acl
  • 6,490
  • 1
  • 27
  • 33
  • when I do the above import, unless I am doing it wrong, all what I get back is the manipulate on the screen! the .m file is correctly on disk. It looks like the import was smart enough to 'process' the .m file during the import and processed it back Manipulate. Please see edit, may be I used the wrong command? – Nasser Sep 11 '11 at 01:02
  • @Nasser, can you post this file somewhere so I'll do it? – acl Sep 11 '11 at 10:08
1

How about something like

nb = EvaluationNotebook[];
NotebookFind[nb, "Code", All, CellStyle]
FrontEndExecute[{FrontEndToken[nb, "Style", "Input"]}]
FrontEndExecute[{FrontEndToken[nb, "SelectionConvert", "StandardForm"]}]

This will convert all "Code" cells to "Input" cells and convert their contents to "StandardForm".

For a list of all FrontEndTokens see belisarius' answer here.


Another option that follows from the recent comment of Rolf Mertig and Alt-Click (or Ctrl-Alt-Click in linux) on a "Code" cell to select all "Code" cells. Then use the Format menu to convert to "Input" style cells and then the Cell menu to Convert To StandardForm. (Alternatively that is Alt-Click on a "Code cell" followed by Alt-9 and then Ctrl-Shift-N)

Community
  • 1
  • 1
Simon
  • 14,631
  • 4
  • 41
  • 101
  • Thanks Simon, I only have ONE cell (it is a demo, the one cell is huge, over 2000 lines long so far). I did the conversion to "StandardForm" of this one cell by using the menu options, but it "mushes" up all the code together, and now I am in the processes of going back and hitting return in all the right places. Please see screen shot I added. There ought to be a better way to do this. my eyes are hurting so much now. – Nasser Sep 10 '11 at 03:35
  • Mathematica really needs a pretty-print build in (user can select from few pre-set modes to format the code according) This is standard in other code--oriented editors. I tried workbench 2.0, copied the source there, but do not see a pretty-print there either. I find this amazing that such an advanced tool does not have a pretty-print build into it. What I am doing should be done by a computer. I am wasting my time instead of working on the algorithm itself. – Nasser Sep 10 '11 at 03:43
  • @Nasser: The cell structure of a notebook makes code formatting less of an issue. The code can be organised in different sections and subsections. And most functionality can be broken into steps that fit into reasonably sized cells. For large blocks of code you have the "Code" cells that don't have automatic formatting and maybe could justify a code-formatting menu - but since they should be written and then hidden, manual formatting is probably enough. – Simon Sep 10 '11 at 04:00
  • @Nasser: Also, we've talked about separating out your large demonstration manipulates before. The code logic and any complicated display functionality should be moved into the initialization *section*. So that the final `Manipulate` just contains just the basic logic and controls - maybe with a small initialization *option*. For example [1](http://demonstrations.wolfram.com/TrigramsAndRealCliffordAlgebras/). Of course in [2](http://demonstrations.wolfram.com/ScalarFeynmanDiagramsAndSymanzikPolynomials/) the WRI reviewer forced me to put all the code in the initialization option, very ugly! – Simon Sep 10 '11 at 04:03
  • Simon, do you know of any pretty-print formating for Mathematica code? I do NOT use any of the special symbols in my code, so it is all plain text. i.e. I can just copy my code to any text editor with no problem. If I can find one which can format the code, then I can just use that editor, and copy the code back to notebook when I want to run it. It is much more important for me to have well formatted code. I tried 2 emacs .el for Mathematica, and none of them have the ability to pretty-print format the code in one shot. thanks. I tried them on linux.... – Nasser Sep 10 '11 at 04:39
  • and I searched google for many other editors (such as notepad++ and such), but none has Mathematica mode. It does not have to be free, I'll buy one if I can find one. – Nasser Sep 10 '11 at 04:40
  • @Nasser in Workbench one may select a function then right click, Source->Format. However, I doubt this does what you want – acl Sep 10 '11 at 14:17
  • @ACL, thanks, I did not see this source-format before. I just tried it, but it did not get it to the original format. I'll just live with 'code' style, the demo is almost over. I tried to get it back using Simon suggestions also, but found number of problems. Next time, I will not do this, and will stick with the 'input'/default cell form. I do like the 'code' style becaase it allows me to format the code as I want, but one has to keep adjusting things all the time using space bar and it gets tiring after a while. The default mode (standard form) is faster to use. – Nasser Sep 10 '11 at 14:45
  • @Nasser what about my suggestion in the comment to your question itself? I could try to implement it but I am not sure I understood what it is you want. – acl Sep 10 '11 at 19:35