recursive traversal through a graph, counting ways to a point - graph

Got a graph which is looks like this one:
I want to count all possible ways to a specific point p(i,j) from p(0,0) in this graph. I think i can do it with Depth-first search. How i should extend the Depth-first search, so its don't count some ways twice?

The best way is to count the number of ways without actually following all of the paths. Let F(x, y) be the number of ways to get to your destination point. Then, you can see that in your graph, F(x, y) = F (x+1, y) + F (x, y+1) + F(x+1, y+1). You want F(0,0). Your base cases are going to be F(i, j) = 1 (one way to get there if you're already there: don't go anywhere) and F(any number > i, any j) and F(i, any number > j) = 0 because there's no way to get to your destination point once you've passed it.
Update with more detail: Now how to evaluate this formula? You could do it recursively, but a naive implementation will be extremely inefficient. A naive implementation would just be something like this in pseudocode that loosely looks like python:
i = ...
j = ...
def paths (x, y):
if (x > i) or (y > j):
return 0
if (x == i) and (y == j):
return 1
else:
return paths (x+1, y) + paths (x, y+1) + paths (x+1, y+1)
print F(0, 0)
The problem with this is that if you start at (0,0), your first level of recursive calls will be (0, 1), (1, 0), and (1, 1). When these calls in turn evaluate, (0, 1) will compute (0, 2) (1, 1), and (1, 2); then (1, 0) will compute (1, 1), (2, 0), and (2, 1), and then (1, 1) will compute (1, 2), (2, 1), and (2, 2). Notice how many of these calls are redundant in that they compute the same value. The technique to resolve this is to keep a matrix that memorizes the values of F. So then the code might look something like this:
i = ...
j = ...
memorizedValues = ... #make an i by j grid filled with -1
memorizedValues[i][j] = 1 #initial condition
def paths (x, y):
if (x > i) or (y > j):
return 0
if (memorizedValues[x][y] != -1): #check for a memorized value before
return memorizedValues[x][y] # starting more recursion!
else:
memorizedValues[x][y] = paths (x+1, y) + paths (x, y+1) + paths (x+1, y+1)
return memorizedValues[x][y]
print F(0, 0)
This is still not the most efficient implementation, but I think it gets the point across. It's considerably faster than counting each path by following it and backtracking!

You can use BFS and either mark the nodes or use a map to keep track of them. However, if your graph is large, BFS entails keeping it all in memory. DFS is better at it. However, DFS can get lost in a large graph unless you put a depth restriction on it.
Anyhow, to speed up your program you might consider stopping early if:
the graph is disconnected
you reach a bridge
Other heuristics:
visit a neighbour of degree 1 first before going any further.
I wrote a somewhat similar program to see how far I can optimize it:
https://github.com/eamocanu/allPathsFinder

Related

Line of Intersection between 2 Planes

I watched and tried to understand bunch of sites and videos about this, and I came into a weird conclusions and some questions. I need some help to explain which one of the method is right, or even both of them are right (but I got different result from each methods).
I'm sorry that I'm bad at explaining things, the first method is solve the equations normally. But, here the link for the video I tried to learn from
https://www.youtube.com/watch?v=o7CfCDkRwfY
Second method is to do cross product for the direction and find the point by set one of the variables as 0. https://www.youtube.com/watch?v=jozabh0lFmo
I tried for this example
x+2y+z−1=0
2x+3y−2z+2=0
and turned out for different answers. Is both of the method are correct, or which one? Thank you.
You have two equations with three unknowns.
You can eliminate one variable and solve for a relationship between the remaining two. Let's eliminate z.
Multiply the first equation by 2:
2x + 4y + 2z = 2
Add this to the second equation:
4x + 7y = 0
You can solve for y as a function of x:
y = -4x/7
Substitute this back into the first equation:
x - 8x/7 + z = 1
Simplify by combining the first and second terms:
-x/7 + z = 1
Solve for z:
z = 1 + x/7
Now you have an equation for the line in 3D space.
-inf <= x <= +inf
y = -4x/7
z = 1 + x/7
Both your equations are satisfied by these two points. Since two points are enough to define a line in Euclidean space I'd say I've got the correct answer.
This line goes through the point (0, 0, 1). It also goes through (7, -4, 2)
Here's a parametric representation of that line for -inf <= t <= +inf:
(x, y, z) = (0, 0, 1) + t*(7, -4, 1)
You can see that when t = 0 (x, y, z) = (0, 0, 1) (first point above) and when t = 1 (x, y, z) = (7, -4, 2) (second point above).
I didn't look at either of your videos. This is how I'd solve it.
This is high school algebra.

Dijsktra worst-case complexity sequence of inputs

I am looking for a sequence of inputs for the Dijsktra algorigthm implemented with a regular heap, where Dijsktras actual complexity would be Θ((e+v)logv).
I know how to implement Dijsktra and how it works, I also understand that the most time consuming operations are adding a vertex to the heap and changing the distance of a vertex. However, I am not sure how to find a graph (sequence of graphs) that would be the worst case inputs for Dijkstra.
Also if you had any general tips on how to find a sequence of inputs for the worst case complexity, that would be helpful.
Let vertices be numbered from 1 to n and you want to find path from vertex 1 to vertex n. Let e[i][j] be length of edge, connecting i and j. Initially e[1][2] = e[2][3] = ... = e[n - 1][n] = 1. Now we iterate through the vertices from n - 2 to 1. In i-th vertex for each j in [i + 2, n] we make e[i][j] = e[i][i + 1] + e[i + 1][j] + 1.
Now we have full graph. In each iteration dijkstra will update O(n) vertices, so it's O(n ^ 2) = O(E) actions working in O(log n).
So final asymptotics will be O(n log(n) + E log(n))

ocaml vector space

I have a R3 space and I'm trying to figure some math "problems" with OCAML functions.
Define function "move", which moves plane based on the plane_name (ex. plane1) and vector (x, y, z):
example:
plane1 = [(1,2,-3); (10,5,2); (-2,3,7)]
move plane1 (1,2,-3);;
- : (int * int * int) list = [(2, 4, -6); (11, 7, -1); (-1, 5, 4)]
Thank you
I'll restrict my answer to problem 3.
I don't know where you're at with OCaml and what limitations have been imposed on your answer. (Forgive me, but I'm assuming this is a homework problem.) Let's assume the point of the exercise is to begin to think recursively. So then you want to write a function like this:
let move plane (x, y, z) = (( code goes here ))
For thinking recursively, the basic insight is that a plane is a list of points and you want to do the same thing to all the points. So a lower-level view of the function would be like this:
let rec move point_list (x, y, z) = (( code goes here ))
Now, a list is either empty, or it isn't. You just need to figure out what to do in each case. Furthermore, when the list is not empty you can use your own function recursively as long as you call it with a smaller list.
If, in fact, the point of this exercise is not to learn recursive thinking, then the answer would be completely different. In particular, there's a function in the List module that would make it pretty easy to solve the problem.
Update
Apparently you want to solve the problem non-recursively. To show how this would work, here is a function that takes two points and adds 1 to the x, y, and z coordinates of both points:
let add1 [(x1, y1, z1); (x2, y2, z2)] =
[(x1 + 1, y1 + 1, z1 + 1); (x2 + 1, y2 + 1, z2 + 1)]
This will cause a compiler warning because it fails for many possible inputs. In particular, it fails whenever the list has some number of points other than 2. To eliminate the warning, we need to decide what we want to return for those cases. Let's say we always return the list unchanged in those cases. Then we get the following:
let add1 = function
| [(x1, y1, z1); (x2, y2, z2)] ->
[(x1 + 1, y1 + 1, z1 + 1); (x2 + 1, y2 + 1, z2 + 1)]
| pts -> pts
I guess you know what you want, but this is not particularly idiomatic OCaml.
Another way to solve the problems non-recursively (without rec) would be to use functions from the List module. That would be much more idiomatic, and in fact is probably what I would do in a real-world situation.

How do I use mathematica to implicitly solve differential equations of a single variable?

I'm trying to force Mathematica to implicitly differentiate an ellipse equation of the form:
x^2/a^2+y^2/b^2 == 100
with a = 8 and b = 6.
The command I'm using looks like this:
D[x^2/a^2 + y^2/b^2 == 100/. y -> 3/4*Sqrt[6400-x^2], x]
where, y->3/4*Sqrt[6400-x^2] comes from solving y in terms of x.
I got this far by following the advice found here: http://www.hostsrv.com/webmaa/app1/MSP/webm1010/implicit
Input for this script is the conventional way that an implicit
relationship beween x and y is expressed in calculus textbooks. In
Mathematica you need to make this relationship explicit by using y[x]
in place of y. This is done automatically in the script by replacing
all occurances of y with y[x].
But the solution Mathematica gives does not have y' or dy/dx in it (like when I solved it by hand). So I don't think it's been solved correctly. Any idea on what command would get the program to solve an implicit differential? Thanks.
The conceptually easiest option (as you mentioned) is to make y a function of x and use the partial derivative operator D[]
In[1]:= D[x^2/a^2 + y[x]^2/b^2 == 100, x]
Solve[%, y'[x]]
Out[1]= (2 x)/a^2 + (2 y[x] y'[x])/b^2 == 0
Out[2]= {{y'[x] -> -((b^2 x)/(a^2 y[x]))}}
But for more complicated relations, it's best to use the total derivative operator Dt[]
In[3]:= SetOptions[Dt, Constants -> {a, b}];
In[4]:= Dt[x^2/a^2 + y^2/b^2 == 100, x]
Solve[%, Dt[y, x]]
Out[4]= (2 x)/a^2 + (2 y Dt[y, x, Constants -> {a, b}])/b^2 == 0
Out[5]= {{Dt[y, x, Constants -> {a, b}] -> -((b^2 x)/(a^2 y))}}
Note that it might be neater to use SetAttributes[{a, b}, Constant] instead of the SetOptions[Dt, Constants -> {a, b}] command... Then the Dt doesn't carry around all that extra junk.
The final option (that you also mentioned) is to solve the original equation for y[x], although this is not always possible...
In[6]:= rep = Solve[x^2/a^2 + y^2/b^2 == 100, y]
Out[6]= {{y -> -((b Sqrt[100 a^2 - x^2])/a)}, {y -> (b Sqrt[100 a^2 - x^2])/a}}
And you can check that it satisfies the differential equation we derived above for both solutions
In[7]:= D[y /. rep[[1]], x] == -((b^2 x)/(a^2 y)) /. rep[[1]]
Out[7]= True
You can substitute your values a = 8 and b = 6 anytime with replacement rule {a->8, b->6}.
If you actually solve your differential equation y'[x] == -((b^2 x)/(a^2 y[x]) using DSolve with the correct initial condition (derived from the original ellipse equation) then you'll recover the solution for y in terms of x given above.

Finding intersect in triangle from a vector originating from a particular side

I know the coordinates of A, B and C.. I also know of a vector V originating from C..
I know that the vector intersects A and B, I just don't know how to find i.
Can anyone explain the steps involved in solving this problem?
Thanks alot.
http://img34.imageshack.us/img34/941/triangleprob.png
If you know A and B, you know equation for the line AB, and you said you know V, so you can form the equation for Line V.... Well i is only point that satisfies both those equations.
Equation for Line AB:
(bx-ax)(Y-ay) = (by-ay)(X-ax)
If you knpow the direction (or slope = m) of the vector, and any point that lies on the vector, then the equation of the line for vector V is
Y = mX = b
where m is the slope or direction of the line, and b is the y coordinate where it crosses thevertical y=axis (where X = 0)
if you know a point on the line (i.e., C = (s, t) then you solve for b by:
t = ms + b ==> b = t - ms,
so equation becomes
Y = mX + t-ms
i = C+kV
Lets call N the normal to the line A,B so N = [-(B-A).y, (B-A).x]
Also, for any point on the line:
(P-A)*N = 0 -- substitute from line 1 above:
(C+kV-A)*N = 0
(kV+C-A)*N = 0
kV*N + (C-A)*N = 0
kV*N = (A-C)*N
k = [(A-C)*N]/V*N
Now that we have k, plug it into line 1 above to get i.
Here I'm using * to represent dot product so expanding to regular multiplication:
k = ((A.x-C.x)*-(B.y-A.y) + (A.y-C.y)*(B.x-A.x)) / (V.x*-(B.y-A.y) + V.x*(B.x-A.x))
I.x = C.x + k*V.x
I.y = C.y + k*V.y
Unless I screwed something up....
Simple algebra. The hard part is often just writing down the basic equations, but once written down, the rest is easy.
Can you define a line that emanates from the point C = [c_x,c_y], and points along the vector V = [v_x,v_y]? A nice way to represent such a line is to use a parametric representation. Thus,
V(t) = C + t*V
In terms of the vector elements, we have it as
V(t) = [c_x + t*v_x, c_y + t*v_y]
Look at how this works. When t = 0, we get the point C back, but for any other value of t, we get some other point on the line.
How about the line segment that passes through A and B? One way to solve this problem would be to define a second line parametrically in the same fashion. Then solve for a system of two equations in two unknowns to find the intersection.
An easier approach is to look at the normal vector to the line segment AB. That vector is given as
N = [b_y - a_y , a_x - b_x]/sqrt((b_x - a_x)^2 + (b_y - a_y)^2)
Note that N is defined here to have a unit norm.
So now, when do we know if a point happens to lie along the line that connects A and B? This is easy now. That will happen when the dot product defined below is exactly zero.
dot(N,V(t) - A) = 0
Expand this, and solve for the parameter t. We can write it down using dot products.
t = dot(N,A-C)/dot(N,V)
Or, if you prefer,
t = (N_x*(a_x - c_x) + N_y*(a_y - c_y)) / (N_x*v_x + N_y*v_y))
And once we have t, substitute into the expression above for V(t). Lets see all of this work in practice. I'll pick some points A,B,C and a vector V.
A = [7, 3]
B = [2, 5]
C = [1, 0]
V = [1, 1]
Our normal vector N, after normalization, will look something like
N = [0.371390676354104, 0.928476690885259]
The line parameter, t, is then
t = 3.85714285714286
And we find the point of intersection as
C + t*V = [4.85714285714286, 3.85714285714286]
If you plot the points on a piece of paper it should all fit together, and all in only a few simple expressions.

Resources