Symbolical mathematical problem (mathematica) - wolfram-mathematica

I got given this question in my tutorial for which I could do parts a) and b). Do you have
any ideas for part c)?
Question :
Symbolically solve the following equation for the quantity r=y/x:
3/y^4==3/x^4+a/(x+2y)^4
(a) Use Map or Thread to perform the substitution y->r x to both sides of the equation.
ans:
3/(r^4 x^4) == 3/x^4 + a/(x + 2 r x)^4
(b) Plot the solutions for a\[Element]{-1,1}. For a\[Element]{-1,1}, how many solutions are real valued? Does this number depend on a ?
ans: Graph and 4 solutions and no its doesn't depend on `a`.
(c) Construct numerical solutions by letting a run between -1 and 1 with steps of 0.02 in your solutions obtained above. Use Cases to choose solutions whenever they are real, and using ListPlot, plot all the real solutions occurring in the interval a\[Element]{-1,1}.
Ans : no idea.

You can shortcut a) and b) by using Eliminate. You can also ask Mathematica to solve equations over reals. (In v8):
In[538]:= eq =
Eliminate[3/y^4 == 3/x^4 + a/(x + 2 y)^4 && r == y/x, {x, y}]
Out[538]= -24 r - 72 r^2 - 96 r^3 + (-45 + a) r^4 + 24 r^5 + 72 r^6 +
96 r^7 + 48 r^8 == 3
In[539]:= r /. Solve[eq && -1 < a < 1, r, Reals]
Out[539]= {ConditionalExpression[
Root[-3 - 24 #1 - 72 #1^2 - 96 #1^3 + (-45 + a) #1^4 + 24 #1^5 +
72 #1^6 + 96 #1^7 + 48 #1^8 &, 1], -1 < a < 0 ||
0 < a < Root[-184528125 + 267553125 #1 + 11238750 #1^2 +
110250 #1^3 - 225 #1^4 + #1^5 &, 1] ||
Root[-184528125 + 267553125 #1 + 11238750 #1^2 + 110250 #1^3 -
225 #1^4 + #1^5 &, 1] < a < 1],
ConditionalExpression[
Root[-3 - 24 #1 - 72 #1^2 - 96 #1^3 + (-45 + a) #1^4 + 24 #1^5 +
72 #1^6 + 96 #1^7 + 48 #1^8 &, 2], -1 < a < 0 ||
0 < a < Root[-184528125 + 267553125 #1 + 11238750 #1^2 +
110250 #1^3 - 225 #1^4 + #1^5 &, 1] ||
Root[-184528125 + 267553125 #1 + 11238750 #1^2 + 110250 #1^3 -
225 #1^4 + #1^5 &, 1] < a < 1],
ConditionalExpression[
Root[-3 - 24 #1 - 72 #1^2 - 96 #1^3 + (-45 + a) #1^4 + 24 #1^5 +
72 #1^6 + 96 #1^7 + 48 #1^8 &, 3],
0 < a < Root[-184528125 + 267553125 #1 + 11238750 #1^2 +
110250 #1^3 - 225 #1^4 + #1^5 &, 1]],
ConditionalExpression[
Root[-3 - 24 #1 - 72 #1^2 - 96 #1^3 + (-45 + a) #1^4 + 24 #1^5 +
72 #1^6 + 96 #1^7 + 48 #1^8 &, 4],
0 < a < Root[-184528125 + 267553125 #1 + 11238750 #1^2 +
110250 #1^3 - 225 #1^4 + #1^5 &, 1]]}
You can then plot the resulting solution:
The Out[539] gives you exact algebraic solutions along with conditions when they are real. So the maximum number of real solutions is 4 and occurs when a is between zero and Root[-184528125 + 267553125 #1 + 11238750 #1^2 + 110250 #1^3 - 225 #1^4 + #1^5 &, 1]
Now, let's get to part c). You should use NSolve to construct all solutions. Then, as suggested Cases to extract real solutions, and then ListPlot:
Table[Thread[{a,
Cases[r /. NSolve[eq, r], r_ /; Im[r] == 0]}], {a, -1, 1,
0.02}] // ListPlot

Related

Time complexity for a recursive function

I'm a computer science student, I got the final exam next week and I got confused trying to find the time complexity for the following function. Can you explain this to me?
int bss(int n){
if(n <= 1)
return n;
return bss(n/2) + bss(n/2);
}
For problems like this, you should figure out the recurrence relation first (by looking at the code), then solve the recurrence relation (using mathematics).
To do step 1, we need to look at each line and see what it contributes to the overall running time T(n) of our algorithm:
int bss(int n){
if(n <= 1) // contributes a constant time a
return n; // contributes a constant time b in the base case only
return bss(n/2) + bss(n/2); // contributes a constant time c
// for the two divisions and one addition,
// plus 2T(n/2)
}
Adding up, we get two cases:
n <= 1: T(n) = a + b
n > 1: T(n) = a + c + 2T(n/2)
To solve this system, we can start writing out terms for values of n. Because we divide n by 2, we might as well choose even n only. Also, it would be nice to have already calculated T(n/2) to calculate T(n); so, we can double our test values of n each time.
n T(n)
---------
1 a + b
2 a + c + 2T(1) = a + c + 2a + 2b = 3a + 2b + c
4 a + c + 2T(2) = a + c + 6a + 4b + 2c = 7a + 4b + 3c
8 a + c + 2T(4) = a + c + 14a + 8b + 6c = 15a + 8b + 7c
16 a + c + 2T(8) = a + c + 30a + 16b + 14c = 31a + 16b + 15c
...
k (2k - 1)a + kb + (k - 1)c
Based on the pattern we saw, it seems as though the solution for n = k is (2k - 1)a + kb + (k - 1)c. We can try to verify this by plugging it into our equations:
k = 1: (2k - 1)a + kb + (k - 1)c = a + b = T(1) ... correct
k > 1:
(2k - 1)a + kb + (k - 1)c ?= a + c + 2[(2k/2 - 1)a + (k/2)b + (k/2 - 1)c]
?= a + c + (2k - 2)a + kb + (k - 2)c
?= a + c + 2ka - 2a + kb + kc - 2c
?= -a -c + 2ka + kb + kc
?= (2k - 1)a + kb + (k - 1)c ... correct
So, we have found a valid solution to our recurrence relation. The solution is:
T(n) = (2n - 1)a + nb + (n - 1)c
Rearranging:
T(n) = (2a + c + 1)n - (a + c)
T(n) is the equation of a line.

How to write a function f("123")=123+12+23+1+2+3 as a recurrence relationship

I'm wondering if someone can help me try to figure this out.
I want f(str) to take a string str of digits and return the sum of all substrings as numbers, and I want to write f as a function of itself so that I can try to solve this with memoization.
It's not jumping out at me as I stare at
Solve("1") = 1
Solve("2") = 2
Solve("12") = 12 + 1 + 2
Solve("29") = 29 + 2 + 9
Solve("129") = 129 + 12 + 29 + 1 + 2 + 9
Solve("293") = 293 + 29 + 93 + 2 + 9 + 3
Solve("1293") = 1293 + 129 + 293 + 12 + 29 + 93 + 1 + 2 + 9 + 3
Solve("2395") = 2395 + 239 + 395 + 23 + 39 + 95 + 2 + 3 + 9 + 5
Solve("12395") = 12395 + 1239 + 2395 + 123 + 239 + 395 + 12 + 23 + 39 + 95 + 1 + 2 + 3 + 9 + 5
You have to break f down into two functions.
Let N[i] be the ith digit of the input. Let T[i] be the sum of substrings of the first i-1 characters of the input. Let B[i] be the sum of suffixes of the first i characters of the input.
So if the input is "12395", then B[3] = 9+39+239+1239, and T[3] = 123+12+23+1+2+3.
The recurrence relations are:
T[0] = B[0] = 0
T[i+1] = T[i] + B[i]
B[i+1] = B[i]*10 + (i+1)*N[i]
The last line needs some explanation: the suffixes of the first i+2 characters are the suffixes of the first i+1 characters with the N[i] appended on the end, as well as the single-character string N[i]. The sum of these is (B[i]*10+N[i]*i) + N[i] which is the same as B[i]*10+N[i]*(i+1).
Also f(N) = T[len(N)] + B[len(N)].
This gives a short, linear-time, iterative solution, which you could consider to be a dynamic program:
def solve(n):
rt, rb = 0, 0
for i in xrange(len(n)):
rt, rb = rt+rb, rb*10+(i+1)*int(n[i])
return rt+rb
print solve("12395")
One way to look at this problem is to consider the contribution of each digit to the final sum.
For example, consider the digit Di at position i (from the end) in the number xn-1…xi+1Diyi-1…y0. (I used x, D, and y just to be able to talk about the digit positions.) If we look at all the substrings which contain D and sort them by the position of D from the end of the number, we'll see the following:
D
xD
xxD
…
xx…xD
Dy
xDy
xxDy
…
xx…xDy
Dyy
xDyy
xxDyy
…
xx…xDyy
and so on.
In other words, D appears in every position from 0 to i once for each prefix length from 0 to n-i-1 (inclusive), or a total of n-i times in each digit position. That means that its total contribution to the sum is D*(n-i) times the sum of the powers of 10 from 100 to 10i. (As it happens, that sum is exactly (10i+1−1)⁄9.)
That leads to a slightly simpler version of the iteration proposed by Paul Hankin:
def solve(n):
ones = 0
accum = 0
for m in range(len(n),0,-1):
ones = 10 * ones + 1
accum += m * ones * int(n[m-1])
return accum
By rearranging the sums in a different way, you can come up with this simple recursion, if you really really want a recursive solution:
# Find the sum of the digits in a number represented as a string
digitSum = lambda n: sum(map(int, n))
# Recursive solution by summing suffixes:
solve2 = lambda n: solve2(n[1:]) + (10 * int(n) - digitSum(n))/9 if n else 0
In case it's not obvious, 10*n-digitSum(n) is always divisible by 9, because:
10*n == n + 9*n == (mod 9) n mod 9 + 0
digitSum(n) mod 9 == n mod 9. (Because 10k == 1 mod n for any k.)
Therefore (10*n - digitSum(n)) mod 9 == (n - n) mod 9 == 0.
Looking at this pattern:
Solve("1") = f("1") = 1
Solve("12") = f("12") = 1 + 2 + 12 = f("1") + 2 + 12
Solve("123") = f("123") = 1 + 2 + 12 + 3 + 23 + 123 = f("12") + 3 + 23 + 123
Solve("1239") = f("1239") = 1 + 2 + 12 + 3 + 23 + 123 + 9 + 39 + 239 + 1239 = f("123") + 9 + 39 + 239 + 1239
Solve("12395") = f("12395") = 1 + 2 + 12 + 3 + 23 + 123 + 9 + 39 + 239 + 1239 + 5 + 95 + 395 + 2395 + 12395 = f("1239") + 5 + 95 + 395 + 2395 + 12395
To get the new terms, with n being the length of str, you are including the substrings made up of the 0-based index ranges of characters in str: (n-1,n-1), (n-2,n-1), (n-3,n-1), ... (n-n, n-1).
You can write a function to get the sum of the integers formed from the substring index ranges. Calling that function g(str), you can write the function recursively as f(str) = f(str.substring(0, str.length - 1)) + g(str) when str.length > 1, and the base case with str.length == 1 would just return the integer value of str. (The parameters of substring are the start index of a character in str and the length of the resulting substring.)
For the example Solve("12395"), the recursive equation f(str) = f(str.substring(0, str.length - 1)) + g(str) yields:
f("12395") =
f("1239") + g("12395") =
(f("123") + g("1239")) + g("12395") =
((f("12") + g("123")) + g("1239")) + g("12395") =
(((f("1") + g("12")) + g("123")) + g("1239")) + g("12395") =
1 + (2 + 12) + (3 + 23 + 123) + (9 + 39 + 239 + 1239) + (5 + 95 + 395 + 2395 + 12395)

Google interview, can somebody confirm this bit string algorithm, pure hypothesis

This was a Google question i didn't figure out was right or wrong but a 2nd opinion never hurt. but the question is "given an n length bit-string solve for the number of times "111" appeared in all possible combinations."
now i know to find total combinations is 2^n what took me trouble was figuring out the number of occurrences i did find a pattern in occurrences but who knows for sure what happens when n becomes vast.
My logical solution was
#Level (n length) # combos # strings with "111" in it
_________________ ________ _____________________________
0 0 0
1("1" or "0") 2 0
2("11","01" etc. 4 0
3 8 1("111")
4 16 3
5 32 8
6 64 20
------------------------------------Everything before this is confirmed
7 128 49
8 256 119
9 512 288
10 1000 696
etc.. i can post how i came up with the magical fairy dust but yeah
I can help you with a solution:
Call the function to calculate number of string with n bit contains 111 is f(n)
If the first bit of the string is 0, we have f(n) += f(n - 1)//0 + (n - 1 bits)
If the first bit of the string is 1, we have f(n) += f(n - 2) + f(n - 3) + 2^(n - 3)
More explanation for case first bit is 1
If the first bit is 1, we have three cases:
10 + (n - 2 bits) = f(n - 2)
110 + (n - 3 bits) = f(n - 3)
111 + (n - 3 bits) = 2^(n - 3) as we can take all combinations.
So in total f(n) = f(n - 1) + f(n - 2) + f(n - 3) + 2^(n - 3).
Apply to our example:
n = 4 -> f(4) = f(3) + f(2) + f(1) + 2^1 = 1 + 0 + 0 + 2 = 3;
n = 5 -> f(5) = f(4) + f(3) + f(2) + 2^2 = 3 + 1 + 0 + 4 = 8;
n = 6 -> f(6) = f(5) + f(4) + f(3) + 2^3 = 8 + 3 + 1 + 8 = 20;
n = 7 -> f(7) = f(6) + f(5) + f(4) + 2^4 = 20 + 8 + 3 + 16 = 47;
n = 8 -> f(8) = f(7) + f(6) + f(5) + 2^5 = 47 + 20 + 8 + 32 = 107;
n = 9 -> f(9) = f(8) + f(7) + f(6) + 2^6 = 107 + 47 + 20 + 64 = 238;

Hamming weight of an interval

My task is to calculate number of 1-bits of interval [1,10^16]. Loop is obviously unusable for this case, and I've heard there exists an algorithm for this. Can anyone help?
More generally, an algorithm for number of 1-bits in an interval [1,n] would be nice.
If that helps, I figured that number of 1-bits of interval [1,2^n-1], n positive integer, is n*2^(n-1).
The number of 1-bits in interval [1,n] is the number of 1-bits in interval [1,2^m] plus the number of 1-bits in interval [1,n-2^m] plus n - 2^m.
m is ⌊log(n)/log2⌋.
Let f(A,B) = the number of 1-bits from A to B, including A and B.
I figured that too : f(1,2^k-1) = k*2^(n-1)
Obviously, f(1, x) = f(0, x) since 0 has no 1-bit.
Let's x = 2^k + b, f(1, x) = f(0, x) = f(0, 2^k + b) = f(0, 2^k - 1) + f(2^k, 2^k + b)
The key problem is f(2^k, 2^k + b)
2^k = 1 0 0 0 ... 0 0
2^k + 1 = 1 0 0 0 ... 0 1
2^k + 2 = 1 0 0 0 ... 1 0
2^k + 3 = 1 0 0 0 ... 0 1
... ...
2^k + b = 1 0 0 0 ... ? ?
Clearly, there is 1-bits in the first bit of each number from 2^k to 2^k + b. And there is (b+1) integers from 2^k to 2^k + b.
We can remove the first 1-bit. And it becomes below.
0 = 0 0 0 0 ... 0 0
1 = 0 0 0 0 ... 0 1
2 = 0 0 0 0 ... 1 0
3 = 0 0 0 0 ... 0 1
... ...
b = 0 0 0 0 ... ? ?
So, f(2^k, 2^k + b) = (b+1) + f(0, b).
f(0, x) = f(0, 2^k - 1) + f(2^k, 2^k + b)
= f(0, 2^k - 1) + (b+1) + f(0, b)
Clearly, we have to recursively calculate f(0,b).
Give an example of step 4.
For f(1, 31) = 80, and 31 has 5 1-bits.
so f(1, 30) = 80 - 5 = 75;
Let's calculate f(1, 30) use the method of step 4.
f(1, 30) = f(0, 30)
= f(0, 15) + f(16, 30)
= 32 + 15 + f(0, 14)
= 47 + f(0, 14)
= 47 + f(0, 7) + f(8, 14)
= 47 + 12 + 7 + f(0, 6)
= 66 + f(0, 6)
= 66 + f(0, 3) + f(4, 6)
= 66 + 4 + 3 + f(0, 2)
= 73 + f(0, 2)
= 73 + f(0, 1) + f(2, 2)
= 74 + f(2, 2)
= 74 + 1 + f(0, 0)
= 75

Mathematica - DSolve spits out #1 in output

I'm not quite certain how to go about interpreting this.
I'm solving a fairly large system of differential equations, DSolve sometimes spits out a list of replacement rules that include terms that have a #1 . I know that #1 is a placeholder for an argument, but I just have no clue where it comes from.
If I have a system of equations similar to
eqs = {
x1'[t] = a1*x1[t] + b1*y1[t]
x2'[t] = a2*x2[t] + b2*y2[t]
...
y1'[t] = c1*y1[t] + d1*x1[t]
y2'[t] = c2*y2[t] + d2*x2[t]}
DSolve[eqs,vars,t] spits out something like
x1 -> e^(-ta1)
x2 -> e^(-t)RootSum[a1a2+a3b4#1 + a3a1b2#1]
...
Obviously a little more complicated but you get the point.
Nothing in the documentation hints as to why this is occurring, And it only happens under certain permuations of parameters (e.g. when I play around with parameters in the original system it either works or doesn't)
This RootSum may be generated by Integrate, which is used by DSolve internally, like so:
In[511]:= Integrate[1/(1 + x + x^2 + x^3 + x^4), x]
Out[511]= RootSum[1 + #1 + #1^2 + #1^3 + #1^4 &,
Log[x - #1]/(1 + 2 #1 + 3 #1^2 + 4 #1^3) &]
It represents a symbolic expression that is the Sum[ Log[x-t]/(1+2*t+3 t^2+4 t^3), {t, {"roots of 1+t+t^2+t^3+t^4"}] (caution, invalid syntax intentional). You can recover the expected normal form using Normal:
In[512]:= Normal[%]
Out[512]=
Log[(-1)^(1/5) + x]/(1 - 2 (-1)^(1/5) + 3 (-1)^(2/5) - 4 (-1)^(3/5)) +
Log[-(-1)^(2/5) + x]/(
1 - 4 (-1)^(1/5) + 2 (-1)^(2/5) + 3 (-1)^(4/5)) +
Log[(-1)^(3/5) + x]/(
1 - 3 (-1)^(1/5) - 2 (-1)^(3/5) + 4 (-1)^(4/5)) +
Log[-(-1)^(4/5) + x]/(1 + 4 (-1)^(2/5) - 3 (-1)^(3/5) + 2 (-1)^(4/5))
Or using the Sum directly:
In[513]:= Sum[
Log[x - t]/(1 + 2*t + 3 t^2 + 4 t^3), {t,
t /. {ToRules[Roots[1 + t + t^2 + t^3 + t^4 == 0, t]]}}]
Out[513]=
Log[(-1)^(1/5) + x]/(1 - 2 (-1)^(1/5) + 3 (-1)^(2/5) - 4 (-1)^(3/5)) +
Log[-(-1)^(2/5) + x]/(
1 - 4 (-1)^(1/5) + 2 (-1)^(2/5) + 3 (-1)^(4/5)) +
Log[(-1)^(3/5) + x]/(
1 - 3 (-1)^(1/5) - 2 (-1)^(3/5) + 4 (-1)^(4/5)) +
Log[-(-1)^(4/5) + x]/(1 + 4 (-1)^(2/5) - 3 (-1)^(3/5) + 2 (-1)^(4/5))
In[514]:= % - %% // FullSimplify
Out[514]= 0

Resources