Changing recursive Closure to TrampolineClosure in Groovy - recursion

I need to construct all possible binary representations from a string containing only the characters 0, 1, and V (the wildcard). The string may be of any length (over 1000 characters) though the number of wildcards is less than 20.
For example, for the input V1V the output would be [010, 011, 110, 111]
My current implementation works but overflows the stack with a modest number of wildcards. The code is running here and shown below.
def permutts
permutts =
{
if (!it.contains('V'))
return [it]
def target = it
def res = []
['0', '1'].each
{
def s = target.replaceFirst(~/V/, it)
if (s.contains('V'))
{
res += permutts(s)
}
else
{
res << s
}
}
res
}
println permutts('V1V')
I've attempted to follow some of the examples of using trampoline() but I'm not even sure if that's the right approach. The API says, "...the function is supposed to perform one step of the calculation..." but each step performs two actions: substituting in 0 and 1 for V.
Here's one of my attempts, which can be run here.
def permutts
permutts =
{ it, res = [] ->
println "entering with " + it + ", res=" + res
if (it.contains('V'))
{
def s = it.replaceFirst(~/V/, '1')
permutts.trampoline(s, res)
s = it.replaceFirst(~/V/, '0')
permutts.trampoline(s, res)
}
else
{
res << it
}
}.trampoline()
println permutts('VV')
The output is:
entering with VV, res=[]
entering with 0V, res=[]
entering with 00, res=[]
[00]
At least it's doing something but I don't understand why it doesn't keep going. Can anyone explain what I'm doing wrong or suggest a different way to tackle this problem?

Groovy's trampoline()provides tail call optimization, so it should be used for closures/methods that invoke themselves in the last instruction executed (tail).
Hence, a better solution would be a classic "head/tail" processing (added println to track calls):
def permutts
permutts = { s, res ->
if (s.length() == 0) {
println "s = $s, res = $res"
res
} else {
println "s = $s, res = $res"
if (s[0] == 'V') { // s[0] ~ list.head()
res = res.collect({ it = it + '0' }) + res.collect({ it = it + '1' })
} else {
res = res.collect({ it = it + s[0] })
}
permutts.trampoline(s.substring(1), res) // s.substring(1) ~ list.tail()
}
}.trampoline()
Examples:
permutts('VV', [''])
s = VV, res = []
s = V, res = [0, 1]
s = , res = [00, 10, 01, 11]
Result: [00, 10, 01, 11]
permutts('0V0', [''])
s = 0V0, res = []
s = V0, res = [0]
s = 0, res = [00, 01]
s = , res = [000, 010]
Result: [000, 010]
Regarding your code, from TrampolineClosure javadoc:
A TrampolineClosure wraps a closure that needs to be executed on a
functional trampoline. Upon calling, a TrampolineClosure will call the
original closure waiting for its result. If the outcome of the call is
another instance of a TrampolineClosure, created perhaps as a result
to a call to the TrampolineClosure.trampoline() method, the
TrampolineClosure will again be invoked. This repetitive invocation of
returned TrampolineClosure instances will continue until a value other
than TrampolineClosure is returned. That value will become the final
result of the trampoline.
That is, the substitution that is made in the tail call optimization. In your code, the whole chain of TrampolineClosures returns as soon as one of them does not return a TrampolineClosure.
From groovy 2.3, you can use #TailRecursive AST transformation for tail call optimization:
import groovy.transform.TailRecursive
#TailRecursive
List permutts(String s, List res = ['']) {
if (s.length() == 0) {
res
} else {
res = (s[0] == 'V') ? res.collect({ it = it + '0' }) + res.collect({ it = it + '1' }) : res.collect({ it = it + s[0] })
permutts(s.substring(1), res)
}
}
EDIT:
Just to complete my answer, the above can be done in one line with the functional fold, which in Groovy is inject (uses the head of the collection as the inital value and iterates over the tail):
assert ['000', '010'] == ['0', 'V', '0'].inject([''], { res, value -> (value == 'V') ? res.collect({ it = it + '0' }) + res.collect({ it = it + '1' }) : res.collect({ it = it + value }) })
assert ['00', '10', '01', '11'] == ['V', 'V'].inject([''], { res, value -> (value == 'V') ? res.collect({ it = it + '0' }) + res.collect({ it = it + '1' }) : res.collect({ it = it + value }) })

Related

Find Path to Sum - recursion

As one of the coding exercise I tried to print the path, which you will encounter to find a particular sum, in this case: 3.
The incrementing values would be 1 and 2.
Thus the shortest path to the sum would return [1,2] or [2,1].
But I can't try to put the path to an array - I have tried putting indexes through the params, but the array would be overwritten (no wonder). Could someone suggest how to tackle this problem?
const toSum = target => {
const calc = sum => {
if (sum == target) return 0;
if (sum > target) return Infinity;
const temp1 = 1 + calc(sum + 2);
const temp2 = 1 + calc(sum + 1);
return Math.min(temp1, temp2);
};
return calc(0);
};
console.log(toSum(3));
pass an array and fill it with the current added value
const toSum = target => {
const calc = (sum ,res) => {
if (sum == 0) return res
if (sum > 2) {
res.push(2)
return calc(sum-2,res)
}
res.push(1)
return calc(sum-1,res)
};
if (target <1 ) return "need to be above 1"
if (!Number.isInteger(target) ) return "need to be an integer"
return calc(target,[])
};
console.log(toSum(3));

The IN operator is provided with too many operands; number of operands: 119 dynamodb

Try to use IN operation in dynamodb but get following error. Could anyone help me with alternative solution ?
var params = {
TableName : "table_name",
FilterExpression : "id IN ("+Object.keys(profileIdObject).toString()+ ")",
ExpressionAttributeValues : profileIdObject
};
ERROR ::
{
"message": "Invalid FilterExpression: The IN operator is provided with too many operands; number of operands: 119",
"code": "ValidationException",
"time": "2018-02-13T08:48:02.597Z",
"statusCode": 400,
"retryable": false,
"retryDelay": 25.08276239472692
}
According to docs:
The maximum number of operands for the IN comparator is 100
Found here: https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Limits.html#limits-expression-parameters
You will need to perform the query/scan in multiple batches, in your case with 100 of Object.keys(profileIdObject).toString() in the first batch and 19 in the second batch. Then coalesce the results.
According to dynamodb documentation, the maximum number of operands for the IN comparator is 100
So you can split into many operations like :
FilterExpression : "id IN (1,2,3, ....) OR id IN (101,102,103,...) ..."
Using this function :
let getFilterExp = function (x) {
let arr = []
let currentIndex = 0
let counter = 0
let max = 99
arr[currentIndex] = {}
for (let y in x) {
if (counter < max) {
arr[currentIndex][y] = x[y]
counter++
}
else {
currentIndex++
arr[currentIndex] = {}
arr[currentIndex][y] = x[y]
counter = 0
}
}
let exp = ''
for (let i = 0; i < arr.length; i++) {
if (i == 0) {
exp += "id IN (" + Object.keys(arr[i]).toString() + ")"
}
else {
exp += " OR id IN (" + Object.keys(arr[i]).toString() + ") "
}
}
return exp
}
Where x is the profileIdObject in your case
let filterExp = getFilterExp(profileIdObject )

How can I convert this large factorial function to a higher-order function?

The following code uses a cache object outside of the factorial function. The factorial function itself is large which has too many concerns of finding factorial and caching.
How can I convert this code to a higher-order function and generate the same result when I call
console.log(factorial(5));
console.log(factorial(7));
cache = { }
function factorial(n) {
if (n === 0) {
return 1;
}
if (cache[n])
{
return cache[n];
}
console.log("Stack Up: " + n);
var value = n * factorial(n - 1);
console.log("Stack Down: " + value);
cache[n] = value;
return value;
}
console.log(factorial(5));
console.log(factorial(7));
There's already other answers out there for memoising recursive functions, but I'll adapt that answer to factorial in javascript so you can see how it works more easily
The secret to writing memoised recursive functions is continuation passing style. A similar technique works when you want to make a non-tail recursive function stack-safe.
I'll leave some console.log statements in this first example so you can see when it's actually computing and when it's just doing a memo lookup.
const memoise = f => {
const memo = new Map()
const compute = (x, k) =>
(console.log('compute', x),
memo.get(x, memo.set(x, f(x,k))))
const lookup = x =>
(console.log('lookup', x),
memo.has(x) ? memo.get(x) : compute(x, lookup))
return lookup
}
const factk = (x, k) => {
if (x === 0)
return 1
else
return x * k(x - 1)
}
const memfact = memoise(factk)
console.log(memfact(5)) // 120
console.log(memfact(7)) // 5040
Here I've removed the console.log calls inside of memoise and instead demonstrate a memoised fibonacci function vs an unmemoised one. Compare the dramatic time difference between memoise(fibk) and badfib
const memoise = f => {
const memo = new Map()
const compute = (x, k) =>
memo.get(x, memo.set(x, f(x,k)))
const lookup = x =>
memo.has(x) ? memo.get(x) : compute(x, lookup)
return lookup
}
const fibk = (x, k) => {
if (x < 2)
return x
else
return k(x - 1) + k(x - 2)
}
const badfib = x => {
if (x < 2)
return x
else
return badfib(x - 1) + badfib(x - 2)
}
console.time('memoised')
console.log(memoise (fibk) (35)) // 9227465 1.46ms
console.timeEnd('memoised')
console.time('unmemoised')
console.log(badfib(35)) // 9227465 135.85ms
console.timeEnd('unmemoised')

Checking if a returned number is an integer in GP/Pari?

This is my first time using GP/Pari and I am having trouble completing this question.
I am asked to print if the return of the function 'wq()' is an integer. Is there a function that can determine if the number passed in is an integer? If not how would I go about checking? I find the syntax somewhat difficult and can't find much information online about it.
I have included what I have so far, any help is appreciated.
wq(x) =
{
[(x-1)! + 1]/x
}
test(r,s) =
{
for (i=r, s, if(isinteger(wq(i)), print("integer"), print("not interger")));
}
If I understand correctly you want to check if (x-1)! + 1 is a multiple of x. You can do that with the modulo operation:
test(r,s) =
{
for (i=r, s, if(Mod((i - 1)! + 1, i) == 0,
print("integer"),
print("not integer")));
}
You can use:
wq(x) =
{
((x-1)! + 1)/x
}
test(r,s) =
{
for (i=r, s, print(if(type(wq(i))=="t_INT", "integer", "not integer")))
}
I changed [] into () since [] gives a row vector (type t_VEC) which is not useful here.
Here is another way to write it:
wq(x) =
{
Mod((x-1)! + 1, x)
}
test(r,s) =
{
for (i=r, s, wq(i) && print1("not "); print("integer"))
}
The function print1 prints and "stays" on the same line. The 'and' operator && "short-circuits". The semicolon ; binds several expressions into one "sequence".

How to eliminate this type of recursion?

This is a bit more intricate than a simple left-recursion or tail-call recursion. So I'm wondering how I can eliminate this kind of recursion. I'm already keeping my own stack as you can see below, so the function needs to no params or return values. However, it's still calling itself up (or down) to a certain level and I want to turn this into a loop, but been scratching my head over this for some time now.
Here's the simplified test case, replacing all "real logic" with printf("dostuff at level #n") messages. This is in Go but the problem is applicable to most languages. Use of loops and goto's would be perfectly acceptable (but I played with this and it gets convoluted, out-of-hand and seemingly unworkable to begin with); however, additional helper functions should be avoided. I guess I should to turn this into some kind of simple state machine, but... which? ;)
As for the practicality, this is to run at about 20 million times per second (stack depth can range from 1 through 25 max later on). This is a case where maintaining my own stack is bound to be more stable / faster than the function call stack. (There are no other function calls in this function, only calculations.) Also, no garbage generated = no garbage collected.
So here goes:
func testRecursion () {
var root *TMyTreeNode = makeSomeDeepTreeStructure()
// rl: current recursion level
// ml: max recursion level
var rl, ml = 0, root.MaxDepth
// node: "the stack"
var node = make([]*TMyTreeNode, ml + 1)
// the recursive and the non-recursive / iterative test functions:
var walkNodeRec, walkNodeIt func ();
walkNodeIt = func () {
log.Panicf("YOUR ITERATIVE / NON-RECURSIVE IDEAS HERE")
}
walkNodeRec = func () {
log.Printf("ENTER LEVEL %v", rl)
if (node[rl].Level == ml) || (node[rl].ChildNodes == nil) {
log.Printf("EXIT LEVEL %v", rl)
return
}
log.Printf("PRE-STUFF LEVEL %v", rl)
for i := 0; i < 3; i++ {
switch i {
case 0:
log.Printf("PRECASE %v.%v", rl, i)
node[rl + 1] = node[rl].ChildNodes[rl + i]; rl++; walkNodeRec(); rl--
log.Printf("POSTCASE %v.%v", rl, i)
case 1:
log.Printf("PRECASE %v.%v", rl, i)
node[rl + 1] = node[rl].ChildNodes[rl + i]; rl++; walkNodeRec(); rl--
log.Printf("POSTCASE %v.%v", rl, i)
case 2:
log.Printf("PRECASE %v.%v", rl, i)
node[rl + 1] = node[rl].ChildNodes[rl + i]; rl++; walkNodeRec(); rl--
log.Printf("POSTCASE %v.%v", rl, i)
}
}
}
// test recursion for reference:
if true {
rl, node[0] = 0, root
log.Printf("\n\n=========>RECURSIVE ML=%v:", ml)
walkNodeRec()
}
// test non-recursion, output should be identical
if true {
rl, node[0] = 0, root
log.Printf("\n\n=========>ITERATIVE ML=%v:", ml)
walkNodeIt()
}
}
UPDATE -- after some discussion here, and further thinking:
I just made up the following pseudo-code which in theory should do what I need:
curLevel = 0
for {
cn = nextsibling(curLevel, coords)
lastnode[curlevel] = cn
if cn < 8 {
if isleaf {
process()
} else {
curLevel++
}
} else if curLevel == 0 {
break
} else {
curLevel--
}
}
Of course the tricky part will be filling out nextsibling() for my custom use-case. But just as a general solution to eliminating inner recursion while maintaining the depth-first traversal order I need, this rough outline should do so in some form or another.
I'm not really sure I understand what it is you want to do since your recursion code looks a little strange. However if I understand the structure of your TMyTreeNode then this is what I would do for a non recursive version.
// root is our root node
q := []*TMyTreeNode{root}
processed := make(map[*TMyTreeNode]bool
for {
l := len(q)
if l < 1 {
break // our queue is empty
}
curr := q[l - 1]
if !processed[curr] && len(curr.childNodes) > 0 {
// do something with curr
processed[curr] = true
q = append(q, curr.childNodes...)
continue // continue on down the tree.
} else {
// do something with curr
processed[curr] = true
q := q[:l-2] // pop current off the queue
}
}
NOTE: This will go arbitrarily deep into the structure. If that's not what you want it will need some modifications.

Resources