Can anybody please help me how this code works,
I am not getting it by myself, some help would be greatly appreciated.
Prime number in scala using recusion:
def isPrime(n: Int): Boolean = {
def isPrimeUntil(t: Int): Boolean =
if (t<=1) true
else n%t != 0 && isPrimeUntil(t-1)
isPrimeUntil(n/2)
}
The number n is prime if and only if there's no number t such that t != 1, t!= n, n % t = 0.
So, if you find some number from 2 to n-1 such that n % t = 0, n is composite, otherwise it is prime.
One more thing, you may see that there's no need to search for divisors among the numbers greater than n/2.
So, all the algorithm does is checks n % d for each t from n/2 to 2. As soon as it is found, the algorithms stops ans says it's composite (returns False). Otherwise it gets to t = 1 and assures the number is prime (returns True).
Just to mention, it's enough to consider the numbers from ceil(sqrt(n)) to 2, which results in better time complexity (O(sqrt(n)) vs O(n)).
isPrime(7) --> isPrimeUntil(3) --> (3 <= 1)? no
(7%3 != 0)? yes
isPrimeUntil(2) --> (2 <= 1)? no
(7%2 != 0)? yes
isPrimeUntil(1) --> (1 <= 1)? yes
isPrime(7) is true. No divisor was found between 1 and 7/2.
isPrime(9) --> isPrimeUntil(4) --> (4 <= 1)? no
(9%4 != 0)? yes
isPrimeUntil(3) --> (3 <= 1)? no
(9%3 != 0)? no
isPrime(9) is false. Found that 9 is divisible by 3.
If you have a local Scala REPL, you should paste this function in there and play around with it. If not, there's always Scastie. I made a Scastie snippet, in which I changed the formatting to my liking, added comments and a demo range.
There are examples of Scala that make it look almost like Malbolge. This one is not that bad.
Let's follow it through with a composite number like 102. Calling isPrime(102) causes isPrimeUntil(51) to be invoked (as 51 is half 102). Since 51 is greater than 1, the nested function calculated 102 % 51, which is 0, so, by "short-circuit evaluation" of logical AND, the nested function should return false.
Now let's try it with 103. Calling isPrime(103) causes isPrimeUntil(51) to be invoked (as 51 is half 103 and the remainder of 1 is simply discarded). Since 51 is greater than 1, the nested function calculated 103 % 51, which is 1, so the nested function calls itself as primeUntil(50). Since 50 is greater than 1, the... so on and so forth until calling itself as primeUntil(1). Since t == 1, primeUntil returns true and the recursion stops.
This gives the wrong answer for negative composite numbers. Plus, as others have mentioned, it is inefficient to start the recursion at n/2. This would be an improvement:
def isPrime(n: Int): Boolean = {
def isPrimeUntil(t: Int): Boolean = {
if (t <= 1) true else n % t != 0 && isPrimeUntil(t - 1)
}
isPrimeUntil(Math.floor(Math.sqrt(Math.abs(n))).toInt)
}
Hmm... it's still giving the wrong answer for −1, 0, 1. But hopefully now you understand this function.
Related
Question: Write a function number_before_reaching_sum that takes an int called sum, which you can assume
is positive, and an int list, which you can assume contains all positive numbers, and returns an int.
You should return an int n such that the first n elements of the list add to less than sum, but the first
n + 1 elements of the list add to sum or more. Assume the entire list sums to more than the passed in
value; it is okay for an exception to occur if this is not the case.
I am quit new on SML, and coudn't find out anything wrong with this simple exprssion. The error message Please help me to debug the code below
fun number_before_reaching_sum (sum:int, xl: int list) =
if hd xl = sum
then 0
else
(hd xl) + number_before_reaching_sum(sum, (tl xl))
Try a couple of steps of your solution on a short list:
number_before_reaching_sum (6, [2,3,4])
--> if 2 = 6
then 0
else 2 + number_before_reaching_sum(6, [3,4])
--> 2 + if 3 = 6
then 0
else 3 + number_before_reaching_sum(6, [4])
--> ...
and you see pretty clearly that this is wrong - the elements of the list should not be added up, and you can't keep looking for the same sum in every tail.
You should return an int n such that the first n elements of the list add to less than sum, but the first n + 1 elements of the list add to sum or more.
This means that the result is 0 if the head is greater than or equal to the sum,
if hd xl >= sum
then 0
Otherwise, the index is one more, not hd xl more, than the index in the tail.
Also the "tail sum" you're looking for isn't the original sum, but the sum without hd xl.
else 1 + number_before_reaching_sum(sum - hd xl, tl xl)
I want to implement a constraint depending on the change of values in my binary decision variable, x, over "time".
I am trying to implement a minimum operating time constraint for a unit commitment optimization problem for power systems. x is representing the unit activation where 0 and 1 show that a power unit, n, at a certain time, t, respectively is shut off or turned on.
For this, indicator constraints seem to be a promising solution and with the inspiration of a similar problem the implementation seemed quite straightforward.
So, since boolean operators are introduced (! and ¬), I prematurely wanted to express the change in a boolean way:
#constraint(m, xx1[n=1:N,t=2:T], (!x[n,t-1] && x[n,t]) => {next(t, 1) + next(t, 2) == 2})
Saying: if unit was deactivated before but now is on, then demand the unit to be active for the next 2 times.
Where next(t, i) = x[((t - 1 + i) % T) + 1].
I got the following error:
LoadError: MethodError: no method matching !(::VariableRef)
Closest candidates are:
!(!Matched::Missing) at missing.jl:100
!(!Matched::Bool) at bool.jl:33
!(!Matched::Function) at operators.jl:896
I checked that the indicator constraint is working properly with a single term only.
Question: Is this possible or is there another obvious solution?
Troubleshooting and workarounds: I have tried the following (please correct me if my diagnosis is wrong):
Implement change as an expression: indicator constraints only work with binary integer variables.
Implement change as another variable relating to x. I have found a solution but it is quite sketchy, which is documented in a Julia discourse. The immediate problem, found from the solution, is that indicator constraints do not work as bi-implication but only one way, LHS->RHS. Please see the proper approach given by #Oscar Dowson.
You can get the working code from github.
The trick is to find constraint(s) that have an equivalent truth-table:
# Like
(!x[1] && x[2]) => {z == 1}
# Is equivalent to:
z >= -x[1] + x[2]
# Proof
-x[1] + x[2] = sum <= z
--------------------------
- 0 + 0 = 0 <= 0
- 1 + 0 = -1 <= 0
- 0 + 1 = 1 <= 1
- 1 + 1 = 0 <= 0
I was recommended MOSEK Modeling Cookbook to help working out the correct formulation of constraints.
See eventually the thread here from where I got the answer for further details.
CodeWars challenges again. Today I have a problem with this one:
"Your task is to split the chocolate bar of given dimension n x m into small squares. Each square is of size 1x1 and unbreakable. Implement a function that will return a minimum number of breaks needed.
For example, if you are given a chocolate bar of size 2 x 1 you can split it to single squares in just one break, but for size 3 x 1 you must do two breaks.
If input data is invalid you should return 0 (as in no breaks are needed if we do not have any chocolate to split). Input will always be a non-negative integer."
For some reason, the output is constantly 0 no matter what sides of the chocolate bar I provide.
What I've already tried:
object breakChocolate {
var result = 0
def breakChocolate(n: Int, m: Int) = {
var t = n*m
var i =0
def breaking(y:Int): Unit ={
if (t ==0 || t ==1)
result = i
else {
breaking(t%2)
i +=1
}
}
result
}
}
Here are the tests:
Test Results:
TestCases
breakChocolate(5, 5) should return 24
Test Failed
0 was not equal to 24
Stack Trace
Completed in 38ms
breakChocolate(7, 4) should return 27
Test Failed
0 was not equal to 27
Stack Trace
Completed in 1ms
Completed in 76ms
To solve this problem you don't need recursion at all. Consider the special case of chocolate plate: (1 x n). To divide this plate completely you need (n-1) breaks. Now you have plate m x n. To divide it into m pieces of form (1 x n) you need (m-1) breaks. So the total number of breaks is
(m-1) + m*(n-1) ~
m - 1 + m*n - m ~
m*n - 1
If I'm reading the Scala correctly, you've got the basic algorithm wrong.
This is actually a very simply problem, something similar to the old puzzle: if you have 55 teams playing in a single-elimination tournament, obviously some of them have to get byes in the first round, so there won't be a perfect even bracket. So how many total games will be played?
The answer: 54. Regardless of how the bracket is made, it's a single-elimination tourney. Every game reduces the number of remaining teams by one. So to get 55 participants down to one winner, 54 games will have to be played.
There is a similar argument to be made for your chocolate bar. At some point, you have p pieces of chocolate in front of you. Whichever one you select to break, you have taken 1 from the pile and put back 2, which means that the pile now has p + 1 pieces. So for every split you add one piece to the pile. This should lead directly to an answer...
...which may actually be wrong because of the need to return 0 in some cases, but it should be easy to special-case that.
You get 0 because you are not running breaking.
If you want to use recursion, one option could be to use a tail recursive function.
First decrement a checking it is greater than 1 to get the number of "horizontal" breaks to get the slices. Add 1 to the accumulator while looping.
Then decrement b checking it is greater than 1 to get the number of "vertical" breaks. This time add the starting "horizonal" value because that is the number of times you actually have to break the slices.
object breakChocolate {
def breakChocolate(n: Int, m: Int): Int = {
def breaking(a: Int, b: Int, acc: Int = 0): Int = {
if (a > 1) breaking(a - 1, b, acc + 1)
else if (b > 1) breaking(a, b - 1, acc + n)
else acc
}
breaking(n, m)
}
}
Scala demo
You can use this code instead:
function breakChocolate(n,m) {
if(n > 0 && m > 0) {
return n * m - 1;
} else {
return 0;
}
}
I am taking coursera course and,for an assignment, I have written a code to count the change of an amount given a list of denominations. A doing a lot of research, I found explanations of various algorithms. In the recursive implementation, one of the base cases is if the amount money is 0 then the count is 1. I don't understand why but this is the only way the code works. I feel that is the amount is 0 then there is no way to make change for it and I should throw an exception. The code look like:
function countChange(amount : Int, denoms :List[Int]) : Int = {
if (amount == 0 ) return 1 ....
Any explanation is much appreciated.
To avoid speaking specifically about the Coursera problem, I'll refer to a simpler but similar problem.
How many outcomes are there for 2 coin flips? 4.
(H,H),(H,T),(T,H),(T,T)
How many outcomes are there for 1 coin flip? 2.
(H),(T)
How many outcomes are there for 0 coin flips? 1.
()
Expressing this recursively, how many outcomes are there for N coin flips? Let's call it f(N) where
f(N) = 2 * f(N - 1), for N > 0
f(0) = 1
The N = 0 trivial (base) case is chosen so that the non-trivial cases, defined recursively, work out correctly. Since we're doing multiplication in this example and the identity element for multiplication is 1, it makes sense to choose that as the base case.
Alternatively, you could argue from combinatorics: n choose 0 = 1, 0! = 1, etc.
So I've spent hours trying to work out exactly how this code produces prime numbers.
lazy val ps: Stream[Int] = 2 #:: Stream.from(3).filter(i =>
ps.takeWhile{j => j * j <= i}.forall{ k => i % k > 0});
I've used a number of printlns etc, but nothings making it clearer.
This is what I think the code does:
/**
* [2,3]
*
* takeWhile 2*2 <= 3
* takeWhile 2*2 <= 4 found match
* (4 % [2,3] > 1) return false.
* takeWhile 2*2 <= 5 found match
* (5 % [2,3] > 1) return true
* Add 5 to the list
* takeWhile 2*2 <= 6 found match
* (6 % [2,3,5] > 1) return false
* takeWhile 2*2 <= 7
* (7 % [2,3,5] > 1) return true
* Add 7 to the list
*/
But If I change j*j in the list to be 2*2 which I assumed would work exactly the same, it causes a stackoverflow error.
I'm obviously missing something fundamental here, and could really use someone explaining this to me like I was a five year old.
Any help would be greatly appreciated.
I'm not sure that seeking a procedural/imperative explanation is the best way to gain understanding here. Streams come from functional programming and they're best understood from that perspective. The key aspects of the definition you've given are:
It's lazy. Other than the first element in the stream, nothing is computed until you ask for it. If you never ask for the 5th prime, it will never be computed.
It's recursive. The list of prime numbers is defined in terms of itself.
It's infinite. Streams have the interesting property (because they're lazy) that they can represent a sequence with an infinite number of elements. Stream.from(3) is an example of this: it represents the list [3, 4, 5, ...].
Let's see if we can understand why your definition computes the sequence of prime numbers.
The definition starts out with 2 #:: .... This just says that the first number in the sequence is 2 - simple enough so far.
The next part defines the rest of the prime numbers. We can start with all the counting numbers starting at 3 (Stream.from(3)), but we obviously need to filter a bunch of these numbers out (i.e., all the composites). So let's consider each number i. If i is not a multiple of a lesser prime number, then i is prime. That is, i is prime if, for all primes k less than i, i % k > 0. In Scala, we could express this as
nums.filter(i => ps.takeWhile(k => k < i).forall(k => i % k > 0))
However, it isn't actually necessary to check all lesser prime numbers -- we really only need to check the prime numbers whose square is less than or equal to i (this is a fact from number theory*). So we could instead write
nums.filter(i => ps.takeWhile(k => k * k <= i).forall(k => i % k > 0))
So we've derived your definition.
Now, if you happened to try the first definition (with k < i), you would have found that it didn't work. Why not? It has to do with the fact that this is a recursive definition.
Suppose we're trying to decide what comes after 2 in the sequence. The definition tells us to first determine whether 3 belongs. To do so, we consider the list of primes up to the first one greater than or equal to 3 (takeWhile(k => k < i)). The first prime is 2, which is less than 3 -- so far so good. But we don't yet know the second prime, so we need to compute it. Fine, so we need to first see whether 3 belongs ... BOOM!
* It's pretty easy to see that if a number n is composite then the square of one of its factors must be less than or equal to n. If n is composite, then by definition n == a * b, where 1 < a <= b < n (we can guarantee a <= b just by labeling the two factors appropriately). From a <= b it follows that a^2 <= a * b, so it follows that a^2 <= n.
Your explanations are mostly correct, you made only two mistakes:
takeWhile doesn't include the last checked element:
scala> List(1,2,3).takeWhile(_<2)
res1: List[Int] = List(1)
You assume that ps always contains only a two and a three but because Stream is lazy it is possible to add new elements to it. In fact each time a new prime is found it is added to ps and in the next step takeWhile will consider this new added element. Here, it is important to remember that the tail of a Stream is computed only when it is needed, thus takeWhile can't see it before forall is evaluated to true.
Keep these two things in mind and you should came up with this:
ps = [2]
i = 3
takeWhile
2*2 <= 3 -> false
forall on []
-> true
ps = [2,3]
i = 4
takeWhile
2*2 <= 4 -> true
3*3 <= 4 -> false
forall on [2]
4%2 > 0 -> false
ps = [2,3]
i = 5
takeWhile
2*2 <= 5 -> true
3*3 <= 5 -> false
forall on [2]
5%2 > 0 -> true
ps = [2,3,5]
i = 6
...
While these steps describe the behavior of the code, it is not fully correct because not only adding elements to the Stream is lazy but every operation on it. This means that when you call xs.takeWhile(f) not all values until the point when f is false are computed at once - they are computed when forall wants to see them (because it is the only function here that needs to look at all elements before it definitely can result to true, for false it can abort earlier). Here the computation order when laziness is considered everywhere (example only looking at 9):
ps = [2,3,5,7]
i = 9
takeWhile on 2
2*2 <= 9 -> true
forall on 2
9%2 > 0 -> true
takeWhile on 3
3*3 <= 9 -> true
forall on 3
9%3 > 0 -> false
ps = [2,3,5,7]
i = 10
...
Because forall is aborted when it evaluates to false, takeWhile doesn't calculate the remaining possible elements.
That code is easier (for me, at least) to read with some variables renamed suggestively, as
lazy val ps: Stream[Int] = 2 #:: Stream.from(3).filter(i =>
ps.takeWhile{p => p * p <= i}.forall{ p => i % p > 0});
This reads left-to-right quite naturally, as
primes are 2, and those numbers i from 3 up, that all of the primes p whose square does not exceed the i, do not divide i evenly (i.e. without some non-zero remainder).
In a true recursive fashion, to understand this definition as defining the ever increasing stream of primes, we assume that it is so, and from that assumption we see that no contradiction arises, i.e. the truth of the definition holds.
The only potential problem after that, is the timing of accessing the stream ps as it is being defined. As the first step, imagine we just have another stream of primes provided to us from somewhere, magically. Then, after seeing the truth of the definition, check that the timing of the access is okay, i.e. we never try to access the areas of ps before they are defined; that would make the definition stuck, unproductive.
I remember reading somewhere (don't recall where) something like the following -- a conversation between a student and a wizard,
student: which numbers are prime?
wizard: well, do you know what number is the first prime?
s: yes, it's 2.
w: okay (quickly writes down 2 on a piece of paper). And what about the next one?
s: well, next candidate is 3. we need to check whether it is divided by any prime whose square does not exceed it, but I don't yet know what the primes are!
w: don't worry, I'l give them to you. It's a magic I know; I'm a wizard after all.
s: okay, so what is the first prime number?
w: (glances over the piece of paper) 2.
s: great, so its square is already greater than 3... HEY, you've cheated! .....
Here's a pseudocode1 translation of your code, read partially right-to-left, with some variables again renamed for clarity (using p for "prime"):
ps = 2 : filter (\i-> all (\p->rem i p > 0) (takeWhile (\p->p^2 <= i) ps)) [3..]
which is also
ps = 2 : [i | i <- [3..], and [rem i p > 0 | p <- takeWhile (\p->p^2 <= i) ps]]
which is a bit more visually apparent, using list comprehensions. and checks that all entries in a list of Booleans are True (read | as "for", <- as "drawn from", , as "such that" and (\p-> ...) as "lambda of p").
So you see, ps is a lazy list of 2, and then of numbers i drawn from a stream [3,4,5,...] such that for all p drawn from ps such that p^2 <= i, it is true that i % p > 0. Which is actually an optimal trial division algorithm. :)
There's a subtlety here of course: the list ps is open-ended. We use it as it is being "fleshed-out" (that of course, because it is lazy). When ps are taken from ps, it could potentially be a case that we run past its end, in which case we'd have a non-terminating calculation on our hands (a "black hole"). It just so happens :) (and needs to ⁄ can be proved mathematically) that this is impossible with the above definition. So 2 is put into ps unconditionally, so there's something in it to begin with.
But if we try to "simplify",
bad = 2 : [i | i <- [3..], and [rem i p > 0 | p <- takeWhile (\p->p < i) bad]]
it stops working after producing just one number, 2: when considering 3 as the candidate, takeWhile (\p->p < 3) bad demands the next number in bad after 2, but there aren't yet any more numbers there. It "jumps ahead of itself".
This is "fixed" with
bad = 2 : [i | i <- [3..], and [rem i p > 0 | p <- [2..(i-1)] ]]
but that is a much much slower trial division algorithm, very far from the optimal one.
--
1 (Haskell actually, it's just easier for me that way :) )