Appending to array within a loop - arrays

I am a SAS programmer learning R.
I have a matrix receivables read from a csv file.
I wish to read the value in the "transit" column, if the value of "id" column of a row is >= 1100000000.
I did this (loop 1):
x = vector()
for (i in 1:length(receivables[,"transit"])){
if(receivables[i,"id"] >= 1100000000){
append(x, receivables[i,"transit"]);
}
}
But, it does not work because after running the loop x is still empty.
>x
logical(0)
However, I was able to accomplish my task with (loop 2):
k=0
x=vector()
for (i in 1:length(receivables[,"transit"])){
if(receivables[i,"id"] >= 1100000000){
k=k+1
x[k] = receivables[i,"transit"]
}
}
Or, with (loop 3):
x = vector()
for (i in 1:length(receivables[,"transit"])){
if(receivables[i,"id"] >= 1100000000){
x <- append(x, receivables[i,"transit"]);
}
}
Why didn't the append function work in the loop as it would in command line?
Actually, to teach me how to fish, what is the attitude/beatitude one must bear in mind when operating functions in a loop as opposed to operating them in command line.
Which is more efficient? Loop 2 or loop 3?

Ok, a few things.
append didn't work in your first attempt because you did not assign the result to anything. In general, R does not work "in place". It is more of a functional language, which means that changes must always be assigned to something. (There are exceptions, but trying to bend this rule too early will get you in trouble.)
A bigger point is that "growing" objects in R is a big no-no. You will quickly start to wonder why anyone could possible use R, because growing objects like this will quickly become very, very slow.
Instead, learn to use vectorized operations, like:
receivables[receivables[,"id"] >= 1100000000,"transit"]

Related

Can a recursive function containing a for loop that contains a call of the mentioned function be implemented using only for loops?

Similar questions have been asked and the general consensus is that anything can be converted from recursion to for loops and vice versa. However, I can't find a way to convert a function of the following pseudocode type to a for loop:
def recursive(n):
if n == 0:
return
for i in range(some_number):
do_sth...
recursive(n-1)
In this case, there is n nested loops and n varies depending on the given argument. When using only for loops, the number of nested loops seems to be always predetermined in the code, it doesn't vary depending on "input". Is there a way to make something like this using only for loops?
Is there a way to make something like this using only for loops?
Well, if you admit a while loop as a case of a pseudocode for loop, at least your example can be made:
def nonrecursive(n):
a = []
z = 0
while n:
while n:
i = z
if i == some_number: break
print((n, i))
a += [[n, i]]
n -= 1
z = 0
if not a: break
n, i = a.pop()
i += 1
z = i
We need to be careful here.
The general true statement is that loops can replace recursion and vice versa. This can be shown lots of ways; see the structured programming theorem for ideas.
Whether for loops can replace recursion depends upon your definitions. Can your for loops run forever, or for an indefinite amount of time not known in advance? If so, they are functionally equivalent to while loops, and they can replace recursion. If your for loops cannot be made to run forever or for an unknown (initially) number of iterations, recursion cannot always be replaced.
Really, it's while loops (plus a stack data structure) that can replace recursion without much trouble.

Looping through a set of sequences satisfying a certain property, without storing them

Below is a MATLAB code (recursion) which inputs a vector (l_1,l_2,...,l_r) of non negative integers and an integer m prints all sequences (m_1,m_2,...,m_r) satisfying:
0 <= m_i <= l_i for all 1 <= i <= r and m_1 + m_2 + ... + m_r = m
The r is captured in the function definition by calling the size of the (l_i) array below:
function arr=sumseq(m,lims)
arr=[];
r=size(lims,2);
if r==0 || m<0
arr=[];
elseif r==1 && lims(1)>=m
arr=[m]; %#ok<NBRAK>
else
for i=0:lims(1)
if(lims(1)<0)
arr=[];
else
v=sumseq(m-i,lims(2:end));
arr=[arr;[i*ones(size(v,1),1) v]];
end
end
end
end
Here what I have done is, stored a whole array of them and made it my output. Instead I want to only print them one by one and not store them in an array. This seems simple enough as there is not much choice in which line(s) I need to change (I believe it is the contents of the else block inside the for loop), but I get into a fix every time I try to achieve it.
(Also, MATLAB warned me that if I kept re-initializing the array with a larger array like in the statement:
arr=[arr;[i*ones(size(v,1),1) v]];
it reallocates a fresh array for all the contents of arr and spends a 'lot' of time doing so.)
In short: recursion or not, I want to save the trouble of storing it, and need an algorithm which is as efficient as or more efficient than what I have here.

How to create a matrix in OCaml?

I'am learning OCaml and currently i'am trying to undertand how iteration works in OCaml and how to create a matrix. I want an array 5 x 5 filled with 0. I know there is an issue with shared references so i created a new array at each iteration however iam having issues in other places, specifically at line 6. Let me know of other issues like indentation practices.
open Array;;
let n = ref 5 and i = ref 0 in
let m = Array.make !n 0 in
while !i < !n do
m.(!i) <- Array.make !n 0;;
i := !i + 1;;
done
m;;
You are using ;; too much. Contrary to popular belief, ;; is not part of ordinary OCaml syntax (in my opinion anyway). It's just a special way to tell the toplevel (the REPL) that you want it to evaluate what you've typed so far.
Leave the ;; after open Array. But change all but the last ;; to ; instead.
(Since you reference the Array module by name in your code, which IMHO is good style, you can also just leave out the open Array;; altogether.)
You want the last ;; because you do want the toplevel to evaluate what you've typed so far.
Your syntax error is caused by the fact that your overall code is like this
let ... in
let ... in
while ... do
...
done
m
The while is one expression (in OCaml everything is an expression) and m is another expression. If you want to have two expressions in a row you need ; between them. So you need ; after done.
You also have a type error. When you create m you're creating an array of ints (your given initial value is 0). So you can't make it into a matrix (an array of arrays) later in the code.
Also (not trying to overload you with criticisms :-) this code reads like imperative code. It's not particularly idiomatic OCaml code. In most people's code, using ref is pretty rare. One immediate improvement I see would just be to say let n = 5. You're not changing the value of n anywhere that I see (though maybe this is part of a larger chunk of code). Another improvement would be to use for instead of while.
Finally, you can do this entire operation in one function call:
let n = 5 in
let m = Array.init n (fun i -> Array.make n 0) in
m
Using explicit loops is actually also quite rare in OCaml (at least in my code).
Or you could try this:
let n = 5 in
let m = Array.make_matrix n n 0 in
m

How to find a loop invariant

I know that the loop invariant is meant to prove the correctness of a problem but i can't quite understand how to come up with one, no matter how trivial the problem is. Here is an example, Can someone point out what are the step i should consider to come up with one. I know that all values that are changing in the loop must be involve in my invariant. Please guide me with this problem, i also have to find the post-condition. An explanation will worth more than an answer; please help.
{M > 0 and N >= 0 }
a = M;
b = N;
k = 1;
while (b > 0) {
if (b % 2 == 0) {
a = a * a;
b = b / 2
} else {
b = b – 1;
k = k * a;
}
}
{ ? ? }
The tricky part about loop invariants is that there is no algorithm (that I'm aware of) that will always guarantee the "correct" answer.
As a start, for the algorithm in your question, try tracing through the program and figure out the goal of the algorithm (Hint: exponents are fun). While tracing keep track of the variables a, b and k.
For example, use M = 2 and N = 1,2,3,.... After a few values of N you'll notice a relationship will start to develop between the variables a, b and k.
Once you figure out the loop invariant the post-condition should be simple to come up with.
Hope this will get the ball rolling for you!
Well, you're going at this a bit backward. As you said, the purpose of the loop invariant is to help you prove the correctness of the program. I guess you didn't write this program -- otherwise you'd know what it was for, and you would have come up with the loop invariant before you wrote the loop, because it's the key to understanding that the loop is correct.
So... what is the program for? How do you know it's correct? The loop invariant will be part of your answer to the second question.
It will sound something like this: At the start and end of every iteration, k=...b.... . After the loop, b==0, so ...., and the program is therefore correct.
I don't want to spell the answer out, because it's probably homework and you'll only learn it if you figure it out yourself.

Haskell : Increment index in a loop

I have a function that calculates f(n) in Haskell.
I have to write a loop so that it will start calculating values from f(0) to f(n), and will every time compare the value of f(i) with some fixed value.
I am an expert in OOP, hence I am finding it difficult to think in the functional way.
For example, I have to write something like
while (number < f(i))
i++
How would I write this in Haskell?
The standard approach here is
Create an infinite list containing all values of f(n).
Search this list until you find what you're after.
For example,
takeWhile (number <) $ map f [0..]
If you want to give up after you reach "n", you can easily add that as a separate step:
takeWhile (number <) $ take n $ map f [0..]
or, alternatively,
takeWhile (number <) $ map f [0 .. n]
You can do all sorts of other filtering, grouping and processing in this way. But it requires a mental shift. It's a bit like the difference between writing a for-loop to search a table, versus writing an SQL query. Think about Haskell as a bit like SQL, and you'll usually see how to structure your code.
You can generate the list of the is such that f i is larger than your number:
[ i | i<-[0..] , f i > number ]
Then, you can simply take the first one, if that's all you want:
head [ i | i<-[0..] , f i > number ]
Often, many idiomatic loops in imperative programming can be rephrased as list comprehensions, or expressed through map, filter, foldl, foldr. In the general case, when the loop is more complex, you can always exploit recursion instead.
Keep in mind that a "blind" translation from imperative to functional programming will often lead to non-idiomatic, hard-to-read code, as it would be the case when translating in the opposite direction. Still, I find it relieving that such translation is always possible.
If you are new to functional programming, I would advise against learning it by translating what you know about imperative programming. Rather, start from scratch following a good book (LYAH is a popular choice).
The first thing that's weird from a functional approach is that it's unclear what the result of your computation is. Do you care about the final result of f (i)? Perhaps you care about i itself. Without side effects everything neends to have a value.
Let's assume you want the final value of the function f (i) as soon as some comparison fails. You can simulate your own while loops using recursion and guards!
while :: Int -> Int -> (Int -> Int) -> Int
while start number f
| val >= number = val
| otherwise = while (start + 1) number f
where
val = f start
Instead of explicit recursion, you can use until e.g.
findGreaterThan :: (Int -> Int) -> Int -> Int -> (Int, Int)
findGreaterThan f init max = until (\(v, i) -> v >= max) (\(v, i) -> (f v, i + 1)) (init, 0)
this returns a pair containing the first value to fail the condition and the number of iterations of the given function.

Resources