43

To my mind, there are at least two cases when For loops are ok: Inside Compile, or in code which is being written with Compile in mind When your inner loops are vectorized or made efficient by some other means, so that each iteration of the For loop is sufficiently intensive computationally Many efficient algorithms are procedural by nature and gain their ...


34

Choosing Adequate Loop-Constructs While there are many loop-like constructs I think there are 5 that every Mathematica programmer should know, 4 of them come as pairs which either do return the result of each iteration or don't, but otherwise share syntax: Map - Scan Table - Do While As a general rule it is a good idea to always use the most simple ...


21

You asked for a general explanation instead of just focusing on specific application examples, so here it goes ... The concepts of "pass by reference" and "pass by value" that you may know from languages like C do not apply very well to Mathematica. Do not try to think in this framework. The right question is not "how to pass by reference/value", but how ...


17

Okay, let's focus on this snippet: Module[{i, j}, Do[ pe = (volume[[j, i + 1]] pi[[j, i + 1]] + volume[[j, i]] pi[[j, i]])/(volume[[j, i]] + volume[[j, i + 1]]) //. Indeterminate -> "*" // Quiet, {i, 1, 8, 1}, {j, 1, 10, 1}]] Creating some dummy data: volume = RandomReal[{-1, 1}, {10, 9}]; pi = RandomReal[{-1, 1}, {10, 9}]; You use ...


13

While While[procedure; test] works, it looks very similar to While[test, procedure]. The only difference is ; vs ,. While is not the most commonly used construct, so when used like this there's a high chance of misunderstanding/misreading. If readability/reliability is a concern (for example a collaboratively developed published package), I'd use the ...


10

If you wrap the body of the loop with Catch, then any Throw will act as Continue: r = 0; Do[Catch[ If[EvenQ[i], Throw[Null]]; r += i ], {i, 10}]; r (* Out: 25 *) (Example taken from the documentation for Continue.)


8

According to the documentation center: Goto first scans any compound expression in which it appears directly, then scans compound expressions that enclose this one. Your Goto - Label construction is part of the List so Mathematica fails to find the label. Taking this under consideration, the following will work: k = 0; Do[{ Label[top]; k = k + 1; ...


8

You need: SetAttributes[myfunc, HoldAll] You then have: myfunc[a_, b_] := {a = 2*a; b = -b;}; vara = 5; varb = 6; SetAttributes[myfunc, HoldAll] myfunc[vara, varb]; {vara, varb} {10, -6} Look for HoldAll, HoldFirst and HoldRest in the documentation and this site. You can do this: myfunc[a_, bIn_] := Block[{b}, {a = 2*a, b = -bIn}]; vara = 5; ...


8

In the Excel object model, the worksheet symbol Cells represents a property, not a method. In Visual Basic and other languages, many properties have a default method called Item. NETLink does not fully implement this notion of a default method: ws@Cells[3, 3]@Value (* 3 *) but: $i = 3; ws@Cells[$i, $i]@Value (* (NETLink`Objects`NETObject$1412516038$...


7

Built-in option This sidesteps most of your code, so it might not be what you are looking for, but I believe your goal can be achieved with Mathematica's built-in image processing capability, specifically: MorphologicalComponents! Define a new clustering function clustering1[config_] := Module[{output, csizes, cindices}, output = ...


7

Table[If[Mod[n!, n^(2 n)] == 0, n], {n, 1, 1000}] /. Null -> Sequence[] {1} Cases[Table[If[Mod[n!, n^(2 n)] == 0, n], {n, 1, 1000}], _?NumericQ] {1} Select[Table[If[Mod[n!, n^(2 n)] == 0, n], {n, 1, 1000}], NumericQ[#] &] {1} DeleteCases[Table[If[Mod[n!, n^(2 n)] == 0, n], {n, 1, 1000}], Null] {1}


7

This duplicates the behavior of yours (no effect on zeroes at ends): smoothee=ReplacePart[#, i_ /; i > 1 && i < Length@# && #[[i]] == 0 :> Mean[{#[[i - 1]], #[[i + 1]]}]] &; smoothee[{0, 1, 3, 4, 6, 8, 0, 11, 12, 0, 13, 0}] (* {0, 1, 3, 4, 6, 8, 19/2, 11, 12, 25/2, 13, 0} *) Here's a goofy (...


7

As I noted in an earlier comment, the ODE to be solved can be rewritten as eq = y'[x] == Log[1 - Exp[-y[x]]] Then, s = First@NDSolve[{y'[x] == Log[1 - Exp[-y[x]]], y[0] == 1}, y, {x, 0, 5}]; Plot[Evaluate[ReIm[y[x] /. s]], {x, 0, 5}, AxesLabel -> {x, y}] where Re[y] is blue, and Im[y] is tan. Because the ODE is singular at y == 0, it is natural to ...


7

f@@(list1 ~Join~ list2) Or, more generally, use @@ to "open" the structure of List: list1 = {x1, x2, x3}; list2 = {y1, y2, y3}; f @@ (list1~Join~list2) f[x1, x2, x3, y1, y2, y3] For a list of lists: listOflists = {list1, list2} f @@ (Flatten@listOflists) f[x1, x2, x3, y1, y2, y3]


7

The problem with your code is that for some values of c, Abs[z] will never become larger than 2. You need to cap the number of iterations. For this type of iteration, the typical function to use is Nest and related functions. countIter[c_] := Length@NestWhileList[ #^2 + c &, 0.0, Abs[#] <= 2 &, 1, 100 (* limit number of ...


7

Clear["Global`*"] eqns = {n == a^3 + b^3, n == c^3 + d^3, 1 <= n <= 10000, a >= b > 0, a > c >= d > 0}; sol = Solve[eqns, {n, a, b, c, d}, Integers] (* {{n -> 1729, a -> 12, b -> 1, c -> 10, d -> 9}, {n -> 4104, a -> 16, b -> 2, c -> 15, d -> 9}} *) And @@ Flatten[eqns /. sol] (* True *)


6

Why not write your own and place it in your init.m file? SetAttributes[DoWhile, HoldAll]; DoWhile[procedure_, test_] := While[procedure; test]


6

If the goal is to perform a parallel search for the first result that meets some condition, then we can consider using ParallelTry instead of throw/catch: ParallelTry[If[PrimeQ[#], #, $Failed]&, Range[492114, 500000]] (* 492227 *) This evaluates a function for every value in the second argument (in parallel). The first result that is anything other ...


6

Here are two possibilities. First, use MovingMap: ClearAll[av]; av[{l_, 0, r_}] := (l + r)/2; av[{_, m_, _}] := m; and then smoothMM[list_] := Join[{First@list}, MovingMap[av, list, 3], {Last@list}] or, you can use in-place assignments: smooth2[list_] := Module[{copy = list, pos = Flatten[Position[list[[2 ;; -2]], 0]] + 1 }, copy[[pos]] = (copy[[...


6

You can replace your subopt initialization and the For loop with: subopt = {x, y} /. FindMinimum[#, {x}, {y}][[2]] & /@ subdtotal Or using Map explicitly {x, y} /. Map[FindMinimum[#, {x}, {y}][[2]] &, subdtotal]


6

You don't actually need to put it in a loop. Mathematica has many other cleaner/faster/shorter ways of implementing this kind of thing. I'll give you three: A Do loop (which you asked for, so it wouldn't be much of an answer if I didn't). An alternative using Map (or /@), which shows up all over the place and is probably one of the most useful Mathematica ...


6

You can improve modestly by using down values instead of Association. Clear[sums]; Timing[ i = 0; day1total = 0; len = Length[day1]; While[ sums[day1total += day1[[Mod[++i, len, 1]]]] =!= 1, sums[day1total] = 1 ]; {i, day1total}] (* Out[94]= {1.65625, {141207, 66105}} *) This gives a factor of 2 on my somewhat slow laptop machine. One can do ...


6

In Mathematica the code to solve your problem is trivial. Like so: With[{n = 15}, Table[FactorInteger[i], {i, n}]] which gives {{{1, 1}}, {{2, 1}}, {{3, 1}}, {{2, 2}}, {{5, 1}}, {{2, 1}, {3, 1}}, {{7, 1}}, {{2, 3}}, {{3, 2}}, {{2, 1}, {5, 1}}, {{11, 1}}, {{2, 2}, {3, 1}}, {{13, 1}}, {{2, 1}, {7, 1}}, {{3, 1}, {5, 1}}} I doubt if any looping code you ...


5

March - this is not a complete answer, but instead addresses the gathering of indices since that seems to be important. Here's a comparison of some methods, tested only on my cigar-lounge netbook so caveat lector. OP - Virgil's original (position based), Virgil - Virgil's adaptation of my first comment, CMT. 2/3 - my second and third comments (gathered ...


5

This should be much faster than using a loop or mapping: rng = 100000; min = 0; max = 10000; k := 0.5; offsets = RandomInteger[{1, 10}, rng]; randomA = RandomReal[{min, max}, rng]; randomB = RandomReal[{min, max}, rng]; effect = xEffect = Range@rng; us = UnitStep[xEffect - offsets - 1]; nr = Pick[Range@Length@effect, us, 0]; nr2 = Pick[Range@Length@...


5

You are trying to find the mean for each channel of an image after masking. So, your code could be much simpler: image = ExampleData[{"TestImage", "Mandrill"}]; mask = DiskMatrix[#1/10, #2] & @@ ImageDimensions@image; channels = Pick[Flatten@#, Flatten@mask, 1] & /@ (ImageData /@ ColorSeparate[image]); Mean /@ channels (* {0.846919, 0.435261, 0....


5

I'd argue that For should be used when you want to iterate through a list of options and insure that they are not run in parallel. To give a silly example, Table[CelebrateBirthday[i],{i,0,18}] is equivalent to For[i=0,i<19,i++,CelebrateBirthday[i]] However, a later programmer might try and performance tune by changing the first example into a ...


5

As alluded to by Daniel Lichtblau you could use TriangleWave with appropriate scaling, e.g. amp = 0.02675; per = 4 amp/0.0001; DiscretePlot[Abs@TriangleWave[{-amp, amp}, x/per], {x, 0, 2 per, 1}, Filling -> None] Compared with @DanielLichtblau comment code: ssk1 = 0.02675; up1 = Table[t, {t, 0, ssk1, .0001}]; down1 = Table[t, {t, ssk1, 0, -.0001}];...


5

Normal[SparseArray[{{i_, j_} /; j != i :> 1/(Sin[i] - Sin[j])}, {5, 5}]] Non-zero diagonal, e.g. Pi: Normal[SparseArray[{{i_,i_} -> Pi, {i_, j_} /; j != i :> 1/(Sin[i] - Sin[j])}, {5, 5}]]


5

You should write your function like so: myFunction[x_] := Module[{y}, y = x; y = y + 3; (y + 3)^3] Note the underscore in x_. This makes x into a formal argument that will not be confused with any definition of x you might have made. Then, even when x and y have global values they will not interfere with either the proper definition of ...


Only top voted, non community-wiki answers of a minimum length are eligible