Expressing the double summation sequence in Raku - math

How to express the double variable double summation sequence in Perl 6?
For an example of double variable double summation sequence see this
It must be expressed as is, i.e. without mathematically reducing the double summation into a single summation. Thank you.

The X (cross operator) and the [+] (reduction metaoperator [ ] with additive operator +) make this surprisingly easy:
To represent1 the double summation ∑³x = 1 ∑⁵y = 1 2x + y , you can do the following:
[+] do for 1..3 X 1..5 -> ($x, $y) { 2 * $x + $y }
# for 1..3 X 1..5 # loop cross values
# -> ($x, $y) # plug into x/y
# { 2 * $x + $y } # calculate each iteration
# do # collect loop return vals
# [+] # sum them all
If you wanted to create a sub for this, you could write it as the following2
sub ΣΣ (
Int $aₒ, Int $aₙ, # to / from for the outer
Int $bₒ, Int $bₙ, # to / from for the inner
&f where .arity = 2  # 'where' clause guarantees only two params
) {
[+] do for $aₒ..$aₙ X $bₒ..$bₙ -> ($a, $b) { &f(a,b) }
}
say ΣΣ 1,3, 1,5, { 2 * $^x + $^y }
Or even simplify things more to
sub ΣΣ (
Iterable \a, # outer values
Iterable \b, # inner values
&f where .arity = 2) { # ensure only two parameters
[+] do f(|$_) for a X b
}
# All of the following are equivalent
say ΣΣ 1..3, 1..5, -> $x, $y { 2 * $x + $y }; # Anonymous block
say ΣΣ 1..3, 1..5, { 2 * $^x + $^y }; # Alphabetic args
say ΣΣ 1..3, 1..5, 2 * * + * ; # Overkill, but Whatever ;-)
Note that by typing it, we can ensure ranges are passed, but by typing it as Iterable rather than Range we can allow more interesting summation sequences, like, say, ΣΣ (1..∞).grep(*.is-prime)[^99], 1..10, { … } that would let us use sequence of the first 100 primes.
In fact, if we really wanted to, we could go overboard, and allow for an arbitrary depth summation operator, which is made easiest by moving the function to the left:
sub ΣΣ (
&function,
**#ranges where # slurp in the ranges
.all ~~ Iterable && # make sure they're Iterables
.elems == &function.arity # one per argument in the function
) {
[+] do function(|$_) for [X] #ranges;
};
Just like [+] sums up all the values of our f() function, [X] calculates the cross iteratively, e.g., [X] 0..1, 3..4, 5..6 first does 0..1 X 3..4 or (0,3),(0,4),(1,3),(1,4), and then does (0,3),(0,4),(1,3),(1,4) X 5..6, or (0,3,5),(0,4,5),(1,3,5),(1,4,5),(0,3,6),(0,4,6),(1,3,6),(1,4,6).
1. Sorry, SO doesn't let me do LaTeX, but you should get the idea. 2. Yes, I know that's a subscript letter O not a zero, subscript numbers aren't valid identifiers normally, but you can use Slang::Subscripts to enable them.

Related

Logic of computing a^b, and is power a keyword?

I found the following code that is meant to compute a^b (Cracking the Coding Interview, Ch. VI Big O).
What's the logic of return a * power(a, b - 1); ? Is it recursion
of some sort?
Is power a keyword here or just pseudocode?
int power(int a, int b)
{ if (b < 0) {
return a; // error
} else if (b == 0) {
return 1;
} else {
return a * power(a, b - 1);
}
}
Power is just the name of the function.
Ya this is RECURSION as we are representing a given problem in terms of smaller problem of similar type.
let a=2 and b=4 =calculate= power(2,4) -- large problem (original one)
Now we will represent this in terms of smaller one
i.e 2*power(2,4-1) -- smaller problem of same type power(2,3)
i.e a*power(a,b-1)
If's in the start are for controlling the base cases i.e when b goes below 1
This is a recursive function. That is, the function is defined in terms of itself, with a base case that prevents the recursion from running indefinitely.
power is the name of the function.
For example, 4^3 is equal to 4 * 4^2. That is, 4 raised to the third power can be calculated by multiplying 4 and 4 raised to the second power. And 4^2 can be calculated as 4 * 4^1, which can be simplified to 4 * 4, since the base case of the recursion specifies that 4^1 = 4. Combining this together, 4^3 = 4 * 4^2 = 4 * 4 * 4^1 = 4 * 4 * 4 = 64.
power here is just the name of the function that is defined and NOT a keyword.
Now, let consider that you want to find 2^10. You can write the same thing as 2*(2^9), as 2*2*(2^8), as 2*2*2*(2^7) and so on till 2*2*2*2*2*2*2*2*2*(2^1).
This is what a * power(a, b - 1) is doing in a recursive manner.
Here is a dry run of the code for finding 2^4:
The initial call to the function will be power(2,4), the complete stack trace is shown below
power(2,4) ---> returns a*power(2,3), i.e, 2*4=16
|
power(2,3) ---> returns a*power(2,2), i.e, 2*3=8
|
power(2,2) ---> returns a*power(2,1), i.e, 2*2=4
|
power(2,1) ---> returns a*power(2,0), i.e, 2*1=2
|
power(2,0) ---> returns 1 as b == 0

How to randomly split a map in Go as evenly as possible?

I have a quick question. I am fairly new to golang. Say I have a map like so:
map[int]string
How could I randomly split it into two maps or arrays and as close to even as possible? So for example, if there are 15 items, it would be split 7 - 8.
For example:
func split(m map[int]string) (odds map[int]string, evens map[int]string) {
n := 1
odds = make(map[int]string)
evens = make(map[int]string)
for key, value := range m {
if n % 2 == 0 {
evens[key] = value
} else {
odds[key] = value
}
n++
}
return odds, evens
}
It is actually an interesting example, because it shows a few aspects of Go that are not obvious for beginners:
range m iterates in a random order, unlike in any other language as far as I know,
the modulo operator % returns the remainder of the integer division,
a function can return several values.
You could do something like this:
myStrings := make(map[int]string)
// Values are added to myStrings
myStrings2 := make(map[int]string)
// Seed system time for random numbers
rand.Seed(time.Now().UTC().UnixNano())
for k, v := range myStrings {
if rand.Float32() < 0.5 {
myStrings2[k] = v
delete(myStrings, k)
}
}
https://play.golang.org/p/6OnH1k4FMu

Pattern Matching SML?

Can someone please explain the: "description of g"? How can f1 takes unit and returns an int & the rest i'm confused about too!!
(* Description of g:
* g takes f1: unit -> int, f2: string -> int and p: pattern, and returns
* an int. f1 and f2 are used to specify what number to be returned for
* each Wildcard and Variable in p respectively. The return value is the
* sum of all those numbers for all the patterns wrapped in p.
*)
datatype pattern = Wildcard
| Variable of string
| UnitP
| ConstP of int
| TupleP of pattern list
| ConstructorP of string * pattern
datatype valu = Const of int
| Unit
| Tuple of valu list
| Constructor of string * valu
fun g f1 f2 p =
let
val r = g f1 f2
in
case p of
Wildcard => f1 ()
| Variable x => f2 x
| TupleP ps => List.foldl (fn (p,i) => (r p) + i) 0 ps
| ConstructorP (_,p) => r p
| _ => 0
end
Wildcard matches everything and produces the empty list of bindings.
Variable s matches any value v and produces the one-element list holding (s,v).
UnitP matches only Unit and produces the empty list of bindings.
ConstP 17 matches only Const 17 and produces the empty list of bindings (and similarly for other integers).
TupleP ps matches a value of the form Tuple vs if ps and vs have the same length and for all i, the i-th element of ps matches the i-th element of vs. The list of bindings produced is all the lists from the nested pattern matches appended together.
ConstructorP(s1,p) matches Constructor(s2,v) if s1 and s2 are the same string (you can compare them with =) and p matches v. The list of bindings produced is the list from the nested pattern match. We call the strings s1 and s2 the constructor name.
Nothing else matches.
Can someone please explain the: "description of g"? How can f1 takes unit and returns an int & the rest i'm confused about too!!
The function g has type (unit → int) → (string → int) → pattern → int, so it takes three (curried) parameters of which two are functions and one is a pattern.
The parameters f1 and f2 must either be deterministic functions that always return the same constant, or functions with side-effects that can return an arbitrary integer / string, respectively, determined by external sources.
Since the comment speaks of "what number to be returned for each Wildcard and Variable", it sounds more likely that the f1 should return different numbers at different times (and I'm not sure what number refers to in the case of f2!). One definition might be this:
local
val counter = ref 0
in
fun uniqueInt () = !counter before counter := !counter + 1
fun uniqueString () = "s" ^ Int.toString (uniqueInt ())
end
Although this is just a guess. This definition only works up to Int.maxInt.
The comment describes g's return value as
[...] the sum of all those numbers for all the patterns wrapped in p.
Since the numbers are not ascribed any meaning, it doesn't seem like g serves any practical purpose but to compare the output of an arbitrarily given set of f1 and f2 against an arbitrary test that isn't given.
Catch-all patterns are often bad:
...
| _ => 0
Nothing else matches.
The reason is that if you extend pattern with additional types of patterns, the compiler will not notify you of a missing pattern in the function g; the catch-all will erroneously imply meaning for cases that are possibly yet undefined.

Map, reduce, filter apply to for loops and while loops

I'm new to Julia and learning use of Map, reduce, filter.
It is becoming very hard for me to comprehend how it can replace for and while loops.
For ex for below code, I would like to replace for loop
function addMultiplesOf3And5(N::Int)
sumOfMultiples = 0
if(N == 3)
return sumOfMultiples + N
end
for i = 3:N-1
if(i % 3 == 0 && i % 5 == 0)
continue
elseif(i % 3 == 0)
sumOfMultiples += i
elseif(i % 5 == 0)
sumOfMultiples += i
end
end
return sumOfMultiples
end
I would really appreciate the help.
Update :
This is what I did after going through tutorials
function addMultiplesOf3And5(N::Int)
array = range(1,N-1)
return reduce(+, map(x -> multiples_of_3_Or_5(x), array))
end
function multiples_of_3_Or_5(n)
if(n % 3 == 0 && n % 5 == 0)
return 0
elseif(n % 3 == 0)
return n
elseif(n % 5 == 0)
return n
else
return 0
end
end
Final:
function addMultiplesOf3And5(N::Int)
array = range(1,N-1)
return reduce(+, filter(x -> ((x%3==0)$(x%5==0)), array))
end
To understand how you can replace your 'for loop + if block' code with 'map / reduce / filter' you need to know exactly how they work and why they might be chosen instead.
1. The map function
map is a function that takes a function variable and a list as arguments, and returns a new list, where each element is the result of applying the function to each element of the old list. So for example if your variable f refers to a function f(x) = x + 5 you defined earlier, and you have a list L=[1,2,3,4,5], then map(f, L) will return [f(L[1]), f(L[2]), f(L[3]), f(L[4]), f(L[5])]
So if you have code like:
f(x) = x + 5;
L = [1,2,3,4,5];
A = zeros(5);
for i in L
A[i] = f(i);
end
You could rewrite this as a mapping operation like so:
A = map(x -> x + 5, [1,2,3,4,5]);
2. The reduce function
reduce takes a binary function variable (i.e. a function that takes two arguments) and a list as arguments. What it does is probably best explained by an example. Calling reduce with the + operator, and list [1,2,3,4,5] will do the following:
Step 1: [1, 2, 3, 4, 5] % : 5 elements
Step 2: [1+2, 3, 4, 5] % [3,3,4,5] : 4 elements
Step 3: [3+3, 4, 5] % [6, 4, 5] : 3 elements
Step 4: [6+4, 5] % [10, 5] : 2 elements
Step 5: [10+5] % [15] : 1 elements
result: 15
i.e. we have reduced the list to a single result by successively applying the binary function to the first pair of elements, consuming the list little by little.
So if you have code like:
f(x,y) = x + y
L = [1,2,3,4,5];
A = L[1];
for i in 2:length(L)
A = f(A, L[i])
end
you could rewrite this as a reduce operation like so:
A = reduce(x,y -> x+y, [1,2,3,4,5])
3. The filter function
filter takes a predicate function (e.g. iseven, isnull, ==, or anything that takes an argument and performs a test on it, resulting in true or false) and a list, tests each element of the list with the function and returns a new list that only contains the elements that pass that test. e.g.
filter(iseven, [1,2,3,4,5]) # returns [2,4]
The answer to your problem
If I understand correctly, addMultiplesOf3And5 takes a number N (e.g. 20), and does the following:
filter out all the elements that can be divided by either 3 or 5 from the list [1,2,3,...,20]
successively add all elements of the resulting list together using a reduce function.
You should be able to use the above to figure out the exact code :)
Not sure what the function in the question is supposed to calculate, but:
addMult3or5(N) = N==3 ? 3 : sum(filter(x->((x%3==0)$(x%5==0)),3:N-1))
calculates the same thing.
sum is a a reduce-like function for the + operation.
Hope this helps clarify.
Also, $ is the exclusive-or operation in Julia.

need help understanding this erlang code

I'm having trouble understanding this line.
[Pid2 ! {delete, V1a}
|| {Pid1a, V1a} <- PV1a, Pid2 <- P2, Pid1a /= Pid2
],
Here is what I understand:
anything before the double pipe "||" is done repeatedly, according what's after the double pipe. so messages with delete atom is repeated sent to Pid2.
I know '/=' mean inequality. I don't understand what '<-' means, and ultimately what the whole line means.
[something(X) || X <- L], is a list comprehension. L is a list of elements, and this expression creates a list of new elements, forming each element by invoking something() on it.
[something(X,Y) || X <-L, Y<-M] is similar, but an element is created for the Cartesian product of each element in X and Y.
[something(X) || X <-L, Expr] is a filter expression. Same as the first one, but it is executed only for elements of L, where Expr is true for the given X.
[something(X) || {X,..} <-L, Expr] is another kind of filter. In the list comprehension only those elements are taken that can be matched by the element.
One more thing to know is that this can not only be used for generating another list, but also for executing a command for each element. If the result of the list comprehension is not matched, the compiler will know not to generate a list at all. This behavior can be used to mimic foreach from other languages.
Some examples:
1> [ X*2 || X <- [1,2,3] ].
[2,4,6]
2> [ X*Y || X <- [1,2], Y <- [3,4,5] ].
[3,4,5,6,8,10]
3> [ X*3 || X <- [1,2,3,4], X rem 2 == 0 ].
[6,12]
4> [ X || {a,X} <- [{a,1},{a,2},{b,3},{c,4}] ].
[1,2]
So your code generates the Cartesian product of all {Pid1a, V1a} elements from PV1a and Pid2 elements from P2, except for those elements where Pid1a equals Pid2, and for each of these pairs sends the {delete, V1a} message to Pid2.
I don't know Erlang, but this looks just like list comprehensions from a bunch of languages I do know. Hopefully this guess will help you until somebody who knows Erlang can answer:
[Pid2 ! {delete, V1a} || {Pid1a, V1a} <- PV1a, Pid2 <- P2, Pid1a /= Pid2],
Translates to imperative-style pseudocode:
For each item in PV1a, unpacking item to {Pid1a, V1a}
For each Pid2 in P2
If Pid1a /= Pid2
Pid2 ! {delete, V1a}
In other words, for each Pid in PV1a and P2, send the message delete V1a to Pid2 as long as Pid1 and Pid2 are not the same Pid.
It is a list comprehension and the <- operator is used for generators.
Look at a more popular introduction example for LCs; to find triangles where the squares of the integer sides equals the square of the integer hypotenuse, but for a given range of integers Ns.
Ns = [1,2,3,4,5,6,7,8,9].
[{X,Y,C} || X <- Ns, Y <- Ns, C <- Ns, X*X + Y*Y == C*C].
This gives us the following list as output.
[{3,4,5},{4,3,5}]
Which seems correct:
3² + 4² = 5²
9 + 16 = 25
25 = 25
So the list comprehension can be read as give us every X,Y and C such that X is taken from Ns, Y is taken from Ns and C is taken from Ns, and X² + Y² equals C².

Resources