0
$\begingroup$

I have read in a Mathematica notebook and have assigned its content to the variable file.

I have created the Strings corresponding to Wolfram Language symbols as follows:

wolframFunctions = #[[2]] & /@ WolframLanguageData[]; 

This list is nice, because I can now use it as an "or" StringPattern.

So if I wanted to find the amount each function is used in the file, I could do the following:

StringCases[
  StringJoin[ (*join notebook sections together *)
   Riffle[(ToString /@ (Flatten@NotebookImport@file)), "____"]], 
  wolframFunctions] // Tally

{{"Hold", 24}, {"C", 877}, {"All", 9}, {"Sin", 7}, {"N", 736}, {"Get",
   9}, {"D", 916}, {"Tr", 154}, {"E", 711}, {"Sec", 4}, {"Simplify", 
  4}, {"I", 841}, {"O", 471}, {"Re", 44}, {"Beta", 3}, {"Pi", 
  9}, {"Solve", 1}, {"Method", 57}, {"Accuracy", 1}, {"Precision", 
  23}, {"Table", 1}, {"List", 1}, {"Plot", 90}, {"Range", 
  74}, {"Style", 108}, {"Thick", 52}, {"Point", 1}, {"Large", 
  1}, {"BaseStyle", 30}, {"Axes", 74}, {"Label", 52}, {"Failure", 
  2}, {"BoxData", 2}, {"RawBoxes", 1}, {"Row", 278}, {"TagBox", 
  176}, {"TemplateBox", 11}, {"Function", 110}, {"Sum", 198}, {"Head",
   11}, {"Mod", 22}, {"False", 231}, {"Pane", 44}, {"Select", 
  33}, {"Grid", 198}, {"Button", 44}, {"Front", 22}, {"Square", 
  22}, {"Plus", 11}, {"Medium", 22}, {"Appearance", 22}, {"Automatic",
   275}, {"Alignment", 66}, {"Graph", 30}, {"RGBColor", 44}, {"Abs", 
  66}, {"Line", 92}, {"AspectRatio", 22}, {"Frame", 88}, {"Tiny", 
  22}, {"Ticks", 44}, {"Gray", 22}, {"Level", 22}, {"BoundaryStyle", 
  22}, {"ScalingFunctions", 22}, {"Padding", 22}, {"Scale", 
  88}, {"Annotation", 77}, {"Left", 22}, {"AutoDelete", 
  44}, {"Spacings", 22}, {"Show", 44}, {"String", 22}, {"Print", 
  22}, {"Top", 22}, {"Baseline", 44}, {"Position", 33}, {"Min", 
  11}, {"Values", 11}, {"With", 11}, {"Times", 1}, {"Magnification", 
  44}, {"Hue", 2}}

where a snippet of the above notebook (file) is:

"HoldComplete[ClearAll[Global`*]]____HoldComplete[Rx[\[Theta]_] := \
{{1, 0, 0}, {0, Cos[\[Theta]], -Sin[\[Theta]]}, {0, Sin[\[Theta]], \
Cos[\[Theta]]}}; , Null, Ry[\[Theta]_] := {{Cos[\[Theta]], 0, Sin[\
\[Theta]]}, {0, 1, 0}, {-Sin[\[Theta]], 0, Cos[\[Theta]]}}; , Null, \
Rz[\[Theta]_] := {{Cos[\[Theta]], -Sin[\[Theta]], 0}, {Sin[\[Theta]], \
Cos[\[Theta]], 0}, {0, 0, 1}}; ]____HoldComplete[GetWx[Rmt_] := \
D[Rmt, t] . Transpose[Rmt]; , Null, GetW[Rmt_] := \
{{GetWx[Rmt][[3]][[2]]}, {GetWx[Rmt][[1]][[3]]}, \
{GetWx[Rmt][[2]][[1]]}}; ]____HoldComplete[(EsfPrimRot = \
Rz[\[Psi]sph[t]]; ) (EsfSecRot = Ry[\[Theta]sph[t]]; ) (EsfTerRot = \
Rx[\[Phi]sph[t]]; ) (PendSecRot = Ry[\[Alpha]pend[t]]; ) (PendPrimRot \
= Rx[\[Beta]pend[t]]; )]____HoldComplete[REsf = EsfPrimRot . \
EsfSecRot . EsfTerRot; , Null, RPend = REsf . PendPrimRot . \
PendSecRot; ]____HoldComplete[DVecPend = RPend . {{0}, {0}, \
{-radioPendulo}}; ]____HoldComplete[(\[CapitalOmega]Esf = \
Simplify[-GetW[Transpose[REsf]]]; ) (\[Omega]Esf = \
Simplify[GetW[REsf]]; ) (\[CapitalOmega]Pend = \
Simplify[-GetW[Transpose[RPend]]]; ) (\[Omega]Pend = \
Simplify[GetW[RPend]]; )]____HoldComplete[(InertiaPendulo = {{IxxP, \
0, 0}, {0, IyyP, 0}, {0, 0, IzzP}}; ) (InertiaSph = {{IxxS, 0, 0}, \
{0, IyyS, 0}, {0, 0, IzzS}}; )]____HoldComplete[(EROTESF = 0.5 \
(Transpose[\[CapitalOmega]Esf] . InertiaSph . \
\[CapitalOmega]Esf)[[1]][[1]]; ) (EROTPEND = 0.5 (Transpose[\
\[CapitalOmega]Pend] . InertiaPendulo . \
\[CapitalOmega]Pend)[[1]][[1]]; )]____HoldComplete[VecEsfera = \
{{x[t]}, {y[t]}, {radioEsfera}}; ]"

and it goes on for a long while with sections and plots, etc

But how could I StringReplace all not wolframFunctions with something like "NotASymbol"?

$\endgroup$
  • $\begingroup$ Let us continue this discussion in chat. $\endgroup$ – creidhne Jul 1 '18 at 23:38
  • $\begingroup$ You could do something like: Tally @ Cases[NotebookImport[file, "Input"], _Symbol?(Context[#] === "System" &), {3, Infinity}, Heads -> True]` $\endgroup$ – Carl Woll Jul 2 '18 at 12:24
1
$\begingroup$

There's a problem using the snippet and StringCases[snippet, wolframFunctions] // Tally. It finds these strings:

{{"Hold", 10}, {"C", 17}, {"All", 1}, {"Sin", 6}, {"N", 5}, {"Get",
9}, {"D", 3}, {"Tr", 5}, {"E", 20}, {"Sec", 4}, {"Simplify", 4}, {"I", 10}, {"O", 2}}

But notice that we found C instead of ClearAll or Cos, Hold instead of HoldComplete, N instead of Null, and Tr but not Transpose. These shorter symbols are not in the snippet.

Instead, make a list of patterns that match wolframFunctions.

wolframPatterns = 
  StringExpression[WordBoundary, #, WordBoundary] & /@ wolframFunctions;

Then use StringCases to match the patterns which makes a better list of matching Wolfram Language symbols:

(myFunctions = StringCases[snippet, wolframPatterns]) // Tally

{{"HoldComplete", 1}, {"ClearAll", 1}, {"Cos", 6}, {"Sin", 6}, {"Null", 4}, {"D", 1}, {"Transpose", 5}, {"Simplify", 4}}

With the improved list of matching functions, let's find "NotASymbol", meaning, strings that are not Wolfram Language symbols:

myStrings = 
 DeleteDuplicates@
  StringCases[snippet, 
   WordBoundary ~~ WordCharacter .. ~~ WordBoundary];
Complement[myStrings, DeleteDuplicates@myFunctions]

$\{0,1,2,3,5,\text{DVecPend},\text{EROTESF},\text{EROTPEND},\text{EsfPrimRot},\text{EsfSecRot},\text{EsfTerRot},\text{GetW},\text{GetWx},\text{Global},\text{InertiaPendulo},\text{InertiaSph},\text{IxxP},\text{IxxS},\text{IyyP},\text{IyyS},\text{IzzP},\text{IzzS},\text{PendPrimRot},\text{PendSecRot},\text{radioEsfera},\text{radioPendulo},\text{REsf},\text{Rmt},\text{RPend},\text{Rx},\text{Ry},\text{Rz},\text{t},\text{VecEsfera},\text{x},\text{y},\text{$\alpha $pend},\text{$\beta $pend},\theta ,\text{$\theta$sph},\text{$\phi$sph},\text{$\psi $sph},\text{$\omega $Esf},\text{$\Omega$Esf},\text{$\omega $Pend},\text{$\Omega $Pend}\}$

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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