Recursive function in Clojure - clojure

I have written a recursive function in java and want to implement the same for Clojure.
The java code snippet is below.
private boolean solve(int i, int j) {
// some other code
if ((solve(i - 1, j)) == true) {
return true;
}
if ((solve(i, j + 1)) == true) {
return true;
}
// some code!!!!
return false;
}
How can this be implemented in Clojure?

an almost direct equivalent is
(defn solve [i j]
(or ;; some other code
(solve (dec i) j)
(solve i (inc j))
;; some code
))
Notice the absence of a return statement - everything is an expression.
In your java snippet "some other code" must have the ability to return truthy, otherwise you end up with a stack overflow (in place of "endless recursion").
The reason the code can be so short is that the or macro short-circuits evaluation (ie. it stops evaluation as soon as a meaningful result can be deduced).
In the clojure example "some other code" must be an expression that could evaluate to false or nil.
If you need to "return false immediately" from "some other code" your expression needs to be a bit more convoluted.

Related

If statement with comparison

I am trying to do a comparison to find the largest number in a list. I know I could just use the (max 1 2 4 3) but I'm trying to write the function myself. However, I'm not too sure where the error is. Whenever I run this, the maximum is always 2. Am I doing a comparison wrong somewhere or forget something?
(defn maxVal [list]
(def maxValue 0)
(doseq [x list]
(println x maxValue)
(if > x maxValue)
(do (println x ">" maxValue)
(def maxValue x)))
(var-get #'maxValue))
(maxVal '(1 4 3 2))
The problem is that your code is evaluating > as a value, not invoking it as a function.
(if > x maxValue)
...evaluates to x, because the function > is neither nil nor false, and thus is truthy when evaluated as a boolean -- and x is in the "if true" position, just as maxValue is in the "else" position in this if. Consequently, the current indentation (while it reflects intent accurately) is a bit misleading; the do should be outside the if, since it takes place no matter what happened prior.
Presumably, what you instead want is:
(if (> x maxValue)

Need a fresh perspective on recursion

I just can't wrap my head around this.
Why do these two functions produce radically different results,
when line 4 seems identical?
Version I
int factorial(int val) // input=5; output=120
{
if (val != 0)
return factorial(val - 1) * val;
return 1;
}
Version II
int factorial(int val) // input=5; output=0
{
if (val != 0)
return factorial(--val) * val;
return 1;
}
They only seem identical if you don't read them - one says val - 1 and the other says --val.
val - 1: Subtraction. Evaluates to the value of val, minus one
--val: Decrement. Reduces val by one, and evaluates to the new value
The latter example has undefined behaviour because you try to read val again on the same line.
Version 2 changes the value of val via the --val, where version 1 only subtracts 1 from val but doesn't update the value of val when doing so.
Use of
return factorial(--val) * val;
is cause for undefined behavior. Don't use it.
For evaluating the expression, the compiler is free to evaluate factorial(--val) first, then evaluate val, and then perform the multiplication. It is also free to evaluate val first, then evaluate factorial(--val), and then perform the multiplication.
If the compiler chooses the first strategy, that statement is equivalent to:
--val;
return factorial(val)*val;
As you can see, that is incorrect.
If the compiler chooses the second strategy, that statement is equivalent to:
int res = factorial(val-1)*val;
--val
return res;
Had the compiler followed this strategy, you'd have gotten the correct answer.
OTOH, the statment
return factorial(val-1)*val;
does not suffer from that problem and always returns the correct value.

Language Independant: Check if a string consists of a multiple of a certain substring

I want the general algorithm to find if a string contains a repeating pattern, and no part of the string is left out of the repeating pattern.
For example, look at these sample strings:
abcabcabc - true
abcabcabcx - false
cucumbercucumber - true
cucumber - false
abaaabaaabaa - true
I looked at this answer, which solved the problem for a few cases, but would fail in case of the cucumber example. I need something that would work in all cases.
A Python solution inspired by https://stackoverflow.com/a/2553533/1763356 is
s in (s + s)[1:-1]
This takes O(n) time assuming an efficient implementation of str.__contains__.
This seems like the obvious way to do it:
String s = "abaaabaabaa" ; // string to test
for (int repeating_pattern_length=1;
repeating_pattern_length<=s.length/2;
repeating_pattern_length++)
{ if (modulo(s.length,repeating_pattern_length)==0)
{ // can fit exactly N times
String proposed_subpattern=s.substring(0,repeating_pattern_length);
for (nth_instance=2; // don't need to check 1st occurrence
nth_instance<=s.length/repeating_pattern_length;
nth_instance++)
{ // check nth occurrence
if (!proposed_subpattern.equal(
s.substring((nth_instance-1)*repeating_pattern_length,
repeating_pattern_length)
cycle repeating_pattern_length; // nth occurrence doesn't match
}
return true;
}
}
return false;
[Untested. This is intended to be Java, but I'm not an expert Java coder. Forgive my trespasses].
This arguably has complexity O(s.length) with a small constant factor.
One might consider building a suffix tree (also linear time) and then checking that the tree has the appropriate cycles. I suspect the above algorithm is pretty good in practice.
Since you aren't asking for a specific language, I'd recommend looking into the Rosetta Code page for Repeating String. You can find and study a bunch of algorithms solving the problem.
Though the problem is stated for 1s and 0s in Rosetta Code, most solutions should work with any possible strings.
I've written a general Common Lisp recursive solution, here the commented code:
(ql:quickload :alexandria)
(defun rep-stringv (a-str &optional (max-rotation (floor (/ (length a-str) 2))))
;; Exit condition if no repetition found.
(cond ((< max-rotation 1) "Not a repeating string")
;; Two checks:
;; 1. Truncated string must be equal to rotation by repetion size.
;; 2. Remaining chars (rest-str) are identical to starting chars (beg-str)
((let* ((trunc (* max-rotation (truncate (length a-str) max-rotation)))
(truncated-str (subseq a-str 0 trunc))
(rest-str (subseq a-str trunc))
(beg-str (subseq a-str 0 (rem (length a-str) max-rotation))))
(and (string= beg-str rest-str)
(string= (alexandria:rotate (copy-seq truncated-str) max-rotation)
truncated-str)))
;; If both checks pass, return the repeting string.
(subseq a-str 0 max-rotation))
;; Recurse function reducing length of rotation.
(t (rep-stringv a-str (1- max-rotation)))))
Testing:
CL-USER> (rep-stringv "cucumber")
"Not a repeating string"
CL-USER> (rep-stringv "abaaabaaabaa")
"abaa"
The best possible solution can be achieved with a suffix tree for the string, as you probably already now - since it's a common problem described everywhere, e.g., Wikipedia.
Implementing it seems overkill to me, unless you really need performance. In any case, examples of suffix trees (in many languages) can be found here.
Here's some elementary C++ code that does the job:
bool IsRepeating( std::string in ) {
int totalLength = in.length();
for (int subLength = 1; subLength <= totalLength / 2; subLength++ ) {
if (totalLength % subLength != 0) continue;
for (int startPos = 0; startPos < subLength; startPos++) {
char startChar =in[startPos];
bool mismatchFound = false;
for (int delta = subLength; delta < totalLength-startPos; delta += subLength) {
if (in[startPos+delta] != startChar ) {
mismatchFound = true;
break;
}
}
if (mismatchFound) {
break;
}
return true;
}
}
return false;
}
It makes use of the fact that the substring length has to be a divisor of the total string length.
The worst-case time complexity is pretty bad, something like O(n^2 log(log(n))), but I'm not sure. (Worst case is when the string consists of exactly two identical substrings.) Still I believe that on average it should perform quite well because most of the outer loop body is only executed for divisors of the string length and the inner loops are aborted as soon as a mismatch is found.
Edit: The solution by #Veedrac is not only much more elegant but also more performant in most cases. For a direct comparison, here's the C++ version:
bool IsRepeating( const std::string& in ) {
if (in.length() < 1) return false;
return (in + in).substr(1, 2 * in.length() - 2).find(in) != std::string::npos;
}
It does however use more memory. And if you don't know the purpose of the function, it might be tough to figure it out. But that also holds for my original version.

Difficulty in understanding let and lambda usage in Scheme

I am having hard time to understand the scope of the following code:
(define (create-counter (x 1))
(let ([count 0])
(lambda()
(let ([temp count])
(set! count (+ x count)) temp))))
if I use:
(let ((c (create-counter ))) (+ (c) (c) (c) (c)))
the code work however if i tried with:
(+ (create-counter)(create-counter)(create-counter)(create-counter))
This does not work and give me a 0. Can someone please help me to understand this thoroughly? if possible, please compare to other language like C/C++ it would be easier for me to catch the hold of this. Thanks
(define (create-counter (x 1))
(let ([count 0])
(lambda()
(let ([temp count])
(set! count (+ x count)) temp))))
Translates to:
auto create_counter(int x=1){
int count=0;
return [x,count]()mutable{
int r=count;
count+=x;
return r;
};
}
A simple C++14 function returning a closure object.
When you do this:
(let ((c (create-counter ))) (+ (c) (c) (c) (c)))
It is:
auto c = create_counter();
auto r = c()+c()+c()+c();
return r;
It creates one counter, then runs it 4 times, returning 0 1 2 3 and adding to 6.
In this case:
(+ ((create-counter))((create-counter))((create-counter))((create-counter)))
It is:
auto r = create_counter()()+create_counter()()+create_counter()()+create_counter()();
return r;
Which creates 4 counters, and runs each one once. The first time you run a counter you get 0. So this adds to 0.
The closure object has state. It returns a bigger number each time you call it.
Now you may not be familiar with C++11/14 lamnda.
auto create_counter(int x=1){
int count=0;
return [x,count]()mutable{
int r=count;
count+=x;
return r;
};
}
Is
struct counter {
int x,count;
int operator()(){
int r=count;
count+=x;
return r;
};
};
counter create_counter(int x=1){
return {x,0};
}
with some syntax sugar.
I fixed what seems to be a syntax error in your original code. I am no expert, so maybe I got it wrong.
As an aside, a briefer create counter looks like:
auto create_counter(int x=1){
return [=,count=0]()mutable{
int r=count;
count+=x;
return r;
};
}
When you call "create-counter", it creates a counter and then returns a procedure that refers to that particular counter. When you call "create-counter" four times, you're creating four separate counters; each procedure refers to its own counter. When you call "create-counter" once and then the resulting procedure four times, it's creating just one counter, and incrementing it four times.
It's a bit hard to compare this to C, since C and C++ are quite weak in the area of closures; it's not easy to return a function that's defined inside of another function.
The closest analog might be a "counter" object in C++; think of "create-counter" as the constructor for an object containing a single integer, and the resulting procedure as an "increment" method that increments the counter contained in that object. In your second example, then, you're creating four distinct objects, where in your first example, you're creating one object and calling its "increment" method four times.

How do I determine if a character is within a range in Clojure?

I'm trying to write a function that checks if a character is within a certain hexadecimal range.
I'm trying the code shown below:
(def current \s)
(and (>= current (char 0x20)) (<= current (char 0xD7FF)))
I get the following error:
java.lang.ClassCastException: java.lang.Character cannot be cast to
java.lang.Number (NO_SOURCE_FILE:0)
I assume because the >= operator expects a number, it tries to type cast it.In regular java, I could just do:
(current >= 0x20) && (current <= 0xD7FF)
explicitly convert it to an int first
(<= 0x20 (int current) 0xD7FF)
Chars aren't numbers in Clojure though it's easy to cast them into characters with the int function.
(number? \a) => false
(number? 42) => true
(number? (int \a)) => true
For casts to primitive types you can use the function with the name of the type you want (see (find-doc #"Coerce")).
(int (char 0x20))
(float ...)
(map double [1 2 3 4])
....