How to initialize multiple variables in a FOR loop in Rust [duplicate] - for-loop

This question already has an answer here:
How to use multiple variables in Rust's for loop?
(1 answer)
Closed last month.
I want initialize multiple variables in a for loop, like for example something like this:
for (i, j) in (1..=4),(10..=16).step_by(2){ println!("i = {i}, j ={j}"); }
The result would be something like:
i = 1, j = 10 i = 2, j = 12 i = 3, j = 14 i = 4, j = 16
I have checked this post: How to use multiple variables in Rust's for loop?
but I haven´t found anything useful for me, I know I can use a while loop, but I find the ability to set everything in just one line much clearer

The zip iterator method, mentioned in the very answer you link to, creates tuples by pairing up elements of two iterators. You can still use it all on one line; there is nothing that requires you to create the two iterators as separate statements.
for (i, j) in (1..=4).zip((10..=16).step_by(2)) {
println!("i = {i}, j ={j}");
}
(Playground)

Related

OpenMP Firstprivate clause

Does anyone know if the following can be an example of firstprivate in openmp?
rowstr[0] = 0;
for (j = 1; j < nrows+1; j++) {
rowstr[j] = rowstr[j] + rowstr[j-1];
}
nza = rowstr[nrows] - 1;
firstprivate variable is rowstr and j is a private variable.
Actually not, if you use the firstprivate clause you may have inconsistency in your output as some values would never be updated, clarifying:
Let's suppose it's an array of size 4 and you have 2 threads, one thread you get iterations 0 and 1 and the other 2 and 3 (in a perfect world). If you use the firstprivate clause the second thread will sum the position 2 of the array with was initially in the array in position 1, instead of summing it with the previous iteration as the sequential version would do.
Not just that, this particular loop have dependency issues and you should use something like a sum reduction in nza.

Testing functions through I/O in Haskell [duplicate]

This question already has answers here:
How to "debug" Haskell with printfs?
(6 answers)
Closed 7 years ago.
I'm playing codewars to sharpen my Haskell skills, and running into a problem that I haven't had in imperative languages.
Let's say I'm writing a function foo() in javascript, which takes an int, adds two, squares it, subtracts one, and returns the square root of that number.
var foo = function(n) {
n += 2;
n = n * n;
n -= 1;
n = Math.sqrt(n);
}
I want to check on the state of the data being processed in the function at various points to help me troubleshoot/revise/debug code, so I will insert console.log() statements whenever I want to see where I'm at. For example, am I, in fact, squaring the sum of n+2 correctly halfway through the function? Let's see...
var foo = function(n) {
n += 2;
n = n * n;
console.log("n = " + n);
n -= 1;
n = Math.sqrt(n);
}
While this example should be simple enough for a Haskeller to write in one line, if you have a complex function and want to check the state at different points, how do Haskellers do it? Is there a standard practice using the IO() monad? Do they get around it some other way?
GHCi has a fancy debugger that lets you step through your code and evaluate it line by line, checking it's state and intermediary results.
But, of course, there is also the printf-style debugging that you are asking for, using the trace function from Debug.Trace. Nothing wrong with using that for small scripts imho, but it's generally discouraged.
trace has the type String -> a -> a, so you pass a string that gets printed (via unsafePerformIO) and any argument that gets simply returned.
In your example we could use it as follows. This is your function translated to Haskell:
foo x = sqrt $ (x+2)**2 - 1
Now we can just add trace and the string we want to see, e.g. "Debug Me: " ++ (show ((x+2)**2)). First import Debug.Trace, though:
import Debug.Trace
foo x = sqrt $ (trace ("Debug Me: " ++ (show ((x+2)**2))) ((x+2)**2)) - 1
A bit ugly? Following David Young's comment below, we better use traceShowId :: Show a => a -> a, if what we want to output is identical to the intermediary result (converted to String, of course):
import Debug.Trace
foo x = sqrt $ (traceShowId ((x+2)**2)) - 1
See here for a summary of debugging options.

Decrementing a loop counter as loop is executing

I'm trying to decrement the counter of a for loop as the loop is running. Unfortunately, Lua doesn't seem to allow that. This piece of code should run forever:
for i = 1, 100 do
print (i)
i = i - 1
end
but it does, in fact, simply print the series 1-100. Is that by design? If so, how do I decrement the counter of a running loop (for example because the current cycle was disqualified and should run again)?
It's by design. From Lua reference manual:
3.3.5 – For Statement
All three control expressions are evaluated only once, before the loop starts. They must all result in numbers.
So modifying the value of i inside the loop won't change how the loop runs.
for i = 10, 1, -1 do
print(i)
end
If you want to step backwards through a table then do:
for i = #SomeTable, 1, -1 do
print(SomeTable[i].someproperty)
end
Yu Hao above linked to the correct manual page, but quoted the wrong part of it.
Here is the correct quote
for v = e1, e2, e3 do block end
is equivalent to the code:
do
local var, limit, step = tonumber(e1), tonumber(e2), tonumber(e3)
if not (var and limit and step) then error() end
while (step > 0 and var <= limit) or (step <= 0 and var >= limit) do
local v = var
block
var = var + step
end
end
[..]
var, limit, and step are invisible variables. The names shown here are for explanatory purposes only.
In other words, the variable that's being looped over (called "var" above) and the variable exposed to the developer (called "v" above) are different. There is no way to access the former.

For Loop: can the end value come from the value of a variable?

I have a forvalues loop:
forvalues x = 1(1)50 {
/* Code goes here */
}
Instead of 50, ideally, I would like that value to come as follows. I have a variable name. Let length = length(name). Whatever the largest value is for length, I would like that to be in place of the 50. I could not figure how to write a forvalues loop in which the end point was not directly stated numerically.
I am thinking that I could deduce the maximum length of the variable as follows:
gen id = 1
gen length = length(name)
by id, sort: egen maxlength = max(length)
From there though I do not know how to store this value into the for loop.
Alternatively, would this be better coded by a while loop?
Something like:
gen x = 1
while (x <= maxlength) {
/* Same Code Here */
replace x = x + 1
}
Based on the documentation I've read, it is possible to use macros but with the caveat that changing the end of the range within the forvalues loop has no effect on the number of times the loop will occur. For instance, if length(name) is 50 when the forvalues loop starts, and you change the length of name within the loop, it will still only loop 50 times.
Technically, you'd be better off using a while loop since forvalues was intended to be used when the end of the range is a literal value. You can use a forvalues loop, but you should use a while loop.
Here's my source to back this up:
http://www.stata.com/manuals13/pforvalues.pdf
Specifically:
Technical note
It is not legal syntax to type
. scalar x = 3
. forvalues i = 1(1)x' {
2. local x =x' + 1
3. display `i'
4. }
forvalues requires literal numbers. Using macros, as shown in the following technical note, is
allowed.
And:
Using macros, as shown in the following technical note, is
allowed.
Technical note
The values of the loop bounds are determined once and for all the first time the loop is executed.
Changing the loop bounds will have no effect. For instance,
will not create an infinite loop. With `n' originally equal to 3, the loop will be performed three
times.
local n 3
forvalues i = 1(1)`n' {
local n = `n' + 1
display `i'
}
Output:
1
2
3
Here is the trick with Stata which I think may work for you. I am using the data auto from Stata datasets.
sysuse auto
Suppose the variable name here be price. Now you want the length of variable price.
sum price
gen length=r(N)
To see what is r(N) type return list after running the sum price.
In your loop it goes like follows: (Updated as per #Nick)
forvalues x = 1/`r(N)'{
/* Code goes here */
}
OR:
local length=r(N)
forvalue i=1/`length'{
dis "`i'"
}
Note: It is not clear why you want for loop.So my answer is restricted to what you only asked for.
#Metrics' first code won't quite work. Here is a better way, cutting out what I call the middle macro.
Start with something more like
. su price, meanonly
. forval j = 1/`r(N)' {
An equivalent approach to the one proposed by #Nick and #Metrics is the following:
sysuse auto, clear
count if !missing(price)
forvalues x = 1 / `r(N)' {
/* Code goes here */
}

Change index variable within ruby loop

I realize this may be against ruby principle and may seem a bit silly, but I am curious to whether it possible to modify the index variable during iteration of a loop in ruby.
This practice is possible in Java/C with the for loop in this contrived example:
for (int k = 0; k < 10; k++)
{
if (k == 5)
k = 8;
}
As well, I am aware that it is possible to access an index variable with Enumerable#each_with_index, but I am interested with the ability to alter the variable in this instance rather than access it.
actually the for semantic is the following:
for(executed_once_before_all; test; execute_every_loop) { /* code */ }
and so, in ruby:
executed_once_before_all
while test do
execute_every_loop
# code
end
so your exemple is like this:
k = 0
while k < 10 do
k = 8 if (k == 5)
k += 1
end
Changing for loop counter in Ruby does not change the number of iterations.
You can change the counter variable, but that will affect the current iteration only:
> for k in 0...10
> k = 8 if k == 5
> puts k
> end
0
1
2
3
4
8 # Note this!
6
7
8
9
The best way to achieve the desired behaviour is to use while loop as #fotanus suggested.
Of course, you can do that with for loop using next statements, but that's much more ugly:
for k in 0...10
next if k > 5 && k <= 8
... do stuff ...
next if k == 5
... do stuff ...
end
You could do that, but Ruby programmers generally don't use the for loop (although it's available). You could also do something like this:
[0,1,2,3,4,5,8,9,10].each do |index|
# your code here
end

Resources