Recursive lambda calculus function - recursion

I would like to create a lambda calculus function P such that (P x y z) gives ((x y)(x P)(P z)). I have tried using variants of the Y-combinator/Turing combinator, i.e. functions of the form λg.(g g), since I need to reproduce the function itself, but I can't see any way forward. Any help would be greatly appreciated.

Basically you want to solve "β-equation" P x y z = (x y) (x P) (P z).
There is a general method of solving equations of the form M = ... M ....
You just wrap the right-hand side in a lambda, forming a term L, where all occurrences of M are replaced by m:
L = λm. ... m ...
Then using a fixed-point combinator you get your solution. Let me illustrate it on your example.
L = λp. (λxyz. (x y) (x p) (p z)),
where λxyz. is a shorthand for λx. λy. λz.
Then, P = Y L, unfolding Y and L we get:
P = (λf. (λg. f (g g)) (λg. f (g g))) (λp. (λxyz. (x y) (x p) (p z)))
->β
(λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g))
// the previous line is our "unfolded" P
Let's check if P does what we want:
P x y z
= // unfolding definition of P
(λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) x y z
->β
((λp. (λxyz. (x y) (x p) (p z))) ((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)))) x y z
->β
(λxyz. (x y) (x ((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)))) (((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g))) z)) x y z
->β
(x y) (x ((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)))) (((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g))) z)
= // folding 1st occurrence of P
(x y) (x P) (((λg. (λp. (λxyz. (x y) (x p) (p z))) (g g)) (λg. (λp. (λxyz. (x y) (x p) (p z))) (g g))) z)
= // folding 2nd occurrence of P
(x y) (x P) (P z)
Q.E.D.

U-combinator should help you create a self-referential lambda abstraction.
Here is Ω, the smallest non-terminating program that exhibits the U-combinator nicely.
((λf. (f f))
(λf. (f f)))
If you can give it a name
Ω := λf.(f f)
Here's what it might look like with your abstraction
((λP. (P P x y z))
(λP. λx. λy. λz. ((x y) (x P) (P z))))
Or using Ω
λx. λy. λz. Ω (λP. λx. λy. λz. ((x y) (x P) (P z))) x y z

Related

How do I draw a rounded rectangle with an arrow (shape of a speech bubble)?

I am trying to create a rounded rectangle with an arrow that looks like this:
I have tried it like this, but only draws a rounded rect, and I don't see where I go wrong.
Does anybody see my mistake?
Thank you!
Public Function SpeechBubbleRight(ByRef r As gdiplus.RECTF, ByVal r1 As Single, ByVal r2 As Single, ByVal r3 As Single, ByVal r4 As Single) As clsWApath
Dim x As Single
Dim Y As Single
Dim w As Single
Dim h As Single
x = r.Left
Y = r.Top
w = r.Width
h = r.Height
Dim rr As New clsWApath
'/''''''
Call rr.Append_Bezier(x, Y + r1, x, Y, x + r1, Y, x + r1, Y)
'---
Call rr.Append_Line(x + r1, Y, x + w - r2, Y)
'''''' \
Call rr.Append_Bezier(x + w - r2, Y, x + w, Y, x + w, Y + r2, x + w, Y + r2)
' |
Call rr.Append_Line(x + w, Y + r2, x + w, Y + h - r3)
' /
Call rr.Append_Bezier(x + w, Y + h - r3, x + w, Y + h, x + w - r3, Y + h, x + w - r3, Y + h)
'__
Call rr.Append_Line(x + w - r3, Y + h, x + r4, Y + h)
'\_
Call rr.Append_Bezier(x + r4, Y + h, x, Y + h, x, Y + h - r4, x, Y + h - r4)
'|
Call rr.Append_Line(x, Y + h - r4, x, Y + r1)
'Add arrow
Dim arrowSize As Single
arrowSize = 20 'Change this value to adjust the size of the arrow
Call rr.Append_Line(x + w, Y + h / 2, x + w + arrowSize, Y + h / 2 - arrowSize / 2)
Call rr.Append_Line(x + w + arrowSize, Y + h / 2 - arrowSize / 2, x + w + arrowSize, Y + h / 2 + arrowSize / 2)
Call rr.Append_Line(x + w + arrowSize, Y + h / 2 + arrowSize / 2, x + w, Y + h / 2)
Call rr.ClosePath
Set SpeechBubbleRight = rr
End Function
Your rasterization library probably expects the lines to be in order; so you should put the segments forming the arrow in the middle of the right edge, splitting it in two:
'/--------\
Call rr.Append_Bezier(x, Y + r1, x, Y, x + r1, Y, x + r1, Y)
Call rr.Append_Line(x + r1, Y, x + w - r2, Y)
Call rr.Append_Bezier(x + w - r2, Y, x + w, Y, x + w, Y + r2, x + w, Y + r2)
' |
' \
' /
' |
Call rr.Append_Line(x + w, Y + r2, x + w, Y + h / 2 - arrowSize / 2)
Call rr.Append_Line(x + w, Y + h / 2 - arrowSize / 2, x + w + arrowSize, Y + h / 2)
Call rr.Append_Line(x + w + arrowSize, Y + h / 2, x + w, Y + h / 2 + arrowSize / 2)
Call rr.Append_Line(x + w, Y + h / 2 + arrowSize / 2, x + w, Y + h - r3)
'\________/
Call rr.Append_Bezier(x + w, Y + h - r3, x + w, Y + h, x + w - r3, Y + h, x + w - r3, Y + h)
Call rr.Append_Line(x + w - r3, Y + h, x + r4, Y + h)
Call rr.Append_Bezier(x + r4, Y + h, x, Y + h, x, Y + h - r4, x, Y + h - r4)
'|
Call rr.Append_Line(x, Y + h - r4, x, Y + r1)
Call rr.ClosePath
Note that you also seem to have a few mistakes in your arrow vertex coordinates, which I also corrected in the code above.

Digital Logic - Implementing Boolean expression using minimum number of 2-input NOR gates

Implement this Boolean expression using a minimum number of 2-input NOR gates. Then, illustrate with a clearly labelled logic circuit diagram.
F(w,x,y) = (x+y)(w+y)(x'+y')
= [(x+y)' + (w+y)' + (x'+y')']' //double negation
= [y'(x'+ w') + xy]'
= [y'(xw)' + xy]'
= [(y+xw)' + (x'+y')']'
= [(y+(x'+w')')' + (x'+y')']'
As far as I know, NOR gate is (x+y)'. From here, I'm confused on how to begin using the result above to produce the logic circuit diagram.
Let's use the notation P ⊥ Q for nor, i.e., for (P + Q)'.
Start here:
1)
[(y+(x'+w')')' + (x'+y')']' = A ⊥ B
where A = (y+(x'+w')')' and B = (x'+y')'
2)
A = y ⊥ D
where D = (x'+w')' = x' ⊥ w'.
3)
B = x' ⊥ y'
4)
x' = x ⊥ 0
y' = y ⊥ 0
Now put everything together:
[(y+(x'+w')')' + (x'+y')']' = A ⊥ B
= (y ⊥ D) ⊥ (x' ⊥ y')
= (y ⊥ (x' ⊥ w')) ⊥ (x' ⊥ y')
= (y ⊥ ((x ⊥ 0) ⊥ (w ⊥ 0))) ⊥ ((x ⊥ 0) ⊥ (y ⊥ 0))
And I bet you will now be able to draw the circuit.

Integrating Norm of vectors

I have two vectors which I want to integrate in Matematica. Let the vectors be
r = {x, y};
Q = {x1, y1};
then I write this command
Integrate[
1/Norm[-((a*Q)/c) + r],
{a, 0, 1},
Assumptions -> (a*x1)/c > x && x ->
Real && (a*x1)/c ->
Real && x > 0 && (a*y1)/c -> Real && (a*y1)/c > y && y > 0
]
Where c is a positive constant. The output yields the same
Integrate[1/Norm[-((a Q)/c) + r], {a, 0, 1},
Assumptions -> (a x1)/c > 0 && (a x1)/c > x && x ->
Real && (a x1)/c -> Real && x > 0 && (a y1)/c > y && y > 0]
Could you please tell me where I am making a mistake?
I would be grateful if you could help me,
Thanks
r = {x, y};
Q = {x1, y1};
Integrate[1/Sqrt[(-((a*Q)/c) + r).(-((a*Q)/c) + r)], {a, 0, 1},
Assumptions -> Element[{x, y, x1, y1, a, c}, Reals]]
Returns:
(*
(1/Sqrt[x1^2 + y1^2])c (-Log[c (-x x1 - y y1 +Sqrt[(x^2 + y^2) (x1^2 + y1^2)])]+
Log[x1^2 + y1^2 - c (x x1 + y y1) +
(c Sqrt[(x1^2 + y1^2) (x1^2 + c^2 (x^2 + y^2) + y1^2 - 2 c (x x1 + y y1))])/
Abs[c]])
*)

2 Dimension Runge-Kutta Method on Mathematica 8

I have a problem while programing in Mathematica 8, here is my code:
f[t_, y_] := {y, y};
RungeKutta3[a_, b_, Alpha_, n_, f_] :=
Module[{h, j, k1, k2, k3},
h = (b - a)/n;
Y = T = Table[0, {100 + 1}];
Y[[1]] = Alpha;
T[[1]] = a;
For[j = 1, j <= n, ++j,
k1 = f[T[[j]], Y[[j]]];
k2 = f[T[[j]] + h/2, Y[[j]] + k1*h/2];
k3 = f[T[[j]] + h, Y[[j]] + (-k1 + 2 k2)h];
Y[[j + 1]] = Y[[j]] + h/6(k1 + 4 k2 + k3);
(* Print[j, "----->", Y[[j]]];*)
T[[j + 1]] = T[[j]] + h;
];];
RungeKutta3[0., 1., {300., 500}, 2, f];
The thing is, I'm trying to implement a Runge-Kutta method. And I was successful actually, but only with a function f[x_] that had 1 dimension. This code is for 2 dimensions, but it simply doesn't work and I don't know why. Here is an example for a code with 1 dimension only (notice that I have to change the first line to define the function and the last line, when I call "RungeKutta3").
f[t_, y_] := y;
RungeKutta3[a_, b_, Alpha_, n_, f_] :=
Module[{h, j, k1, k2, k3},
h = (b - a)/n;
Y = T = Table[0, {100 + 1}];
Y[[1]] = Alpha;
T[[1]] = a;
For[j = 1, j <= n, ++j,
k1 = f[T[[j]], Y[[j]]];
k2 = f[T[[j]] + h/2, Y[[j]] + k1*h/2];
k3 = f[T[[j]] + h, Y[[j]] + (-k1 + 2 k2)*h];
Y[[j + 1]] = Y[[j]] + h/6*(k1 + 4 k2 + k3);
(* Print[j, "----->", Y[[j]]];*)
T[[j + 1]] = T[[j]] + h;
];];
RungeKutta3[0., 1., 300., 100, f];
To sum up, how do I implemented the Runge-Kutta method for a function with 2 dimensions??
If you could help me out I would be grateful.
Thanks in advance!
PS: the Runge-Kutta method is order 3
----------------------
Problem solved! Check the code, if anybody needs help with anything, just ask!
f[t_, y1_, y2_] := 3 t*y2 + Log[y1] + 4 y1 - 2 t^2 * y1 - Log[t^2 + 1] - t^2;
F[t_, {y1_, y2_}] := {y2, f[t, y1, y2]};
RungeKutta3[a_, b_, [Alpha]_, n_, f_] :=
Module[{h, j, k1, k2, k3, Y, T, R},
h = (b - a)/n;
Y = T = Table[0, {n + 1}];
Y[[1]] = [Alpha]; T[[1]] = a;
For[j = 1, j <= n, ++j,
k1 = f[T[[j]], Y[[j]]];
k2 = f[T[[j]] + h/2, Y[[j]] + k1*h/2];
k3 = f[T[[j]] + h, Y[[j]] + (-k1 + 2 k2)*h];
Y[[j + 1]] = Y[[j]] + h/6*(k1 + 4 k2 + k3);
T[[j + 1]] = T[[j]] + h;
];
R = Table[0, {n + 1}];
For[j = 1, j <= n + 1, j++, R[[j]] = Y[[j]][[1]]];
Print[ListPlot[Transpose[{T, R}]]]
];
RungeKutta3[0., 1, {1., 0.}, 1000, F];
I know basically have a mathematica program that can solve ANY 2nd order equation! Through Runge-Kutta method. just insert your function on
f[t_, y1_, y2_]:= [Insert your function here]
where t is the independent value, y1 is the function itself y(t), y2 is y'(t).
Call the function through:
RungeKutta3[a, b, [Alpha], n, F];
where a is the initial "t" value, b the final "t" value, [Alpha] the initial value of your function and the first derivative (given in the form {y1(a),y2(a0)}), n the number of points equally spaced you want to represent. F is the function you have to insert despite of the function you give to f
Any questions feel free to ask!!
PS: The Runge-Kutta problem solves differential equations with problems of initial values, i used this program as a base to solve a problem of boundary values, if you want it just text me!
Doesn't your code just implement what is already built into Mathematica, namely, if you were to use the option
Method -> {"ExplicitRungeKutta", "DifferenceOrder" -> 3}
to NDSolve?
(This is not to suggest there's no value in "rolling your own": perhaps you want to do it as a learning exercise for yourself or for students, or as a student yourself.)

Result in an argument isn't correct

So I have this piece of prolog code:
my_avalia(A, R) :-
A == "Koza" -> koza(R, 0, 0, e, 89).
koza(R, _, _, _, 87) :-
!,
write(R).
koza(R, X, Y, V, C) :-
movex(V, X, X1),
movey(V, Y, Y1),
confirma(X1, Y1, Z),
Z == 1 -> (append(R, [emFrente], U),
L is (C - 1),
koza(U, X1, Y1, V, L)).
The matter is that when I write the "R" at koza(), it has the correct values, however it ends up with a empty list in my_avalia when I call it like this:
my_avalia("Koza",R).
My recursion might be incorrect but I don't really know what's wrong with it.
Thanks in advance.
The other functions:
movex(X,Y,R):-(X==o)->(R is Y-1).
movex(X,Y,R):-(X==n)->(R is Y).
movex(X,Y,R):-(X==s)->(R is Y).
movex(X,Y,R):-(X==e)->(R is Y+1).
movey(X,Y,R):-(X==n)->(R is Y-1).
movey(X,Y,R):-(X==s)->(R is Y+1).
movey(X,Y,R):-(X==o)->(R is Y).
movey(X,Y,R):-(X==e)->(R is Y).
confirma(X,Y,R):-(santafe(X,Y),R is 1); (R is 0).
I figured it out.. Such a silly mistake.
koza([], _, _, _, 87) :-!.
koza(R, X, Y, V, C) :-
movex(V, X, X1),
movey(V, Y, Y1),
confirma(X1, Y1, Z),
Z == 1 -> (L is (C - 1),
koza(U, X1, Y1, V, L),
append(U, [emFrente], R)).
Thanks anyway.
koza([], _, _, _, 87) :-!.
koza(R, X, Y, V, C) :-
movex(V, X, X1),
movey(V, Y, Y1),
confirma(X1, Y1, Z),
Z == 1 -> (L is (C - 1),
koza(U, X1, Y1, V, L),
append(U, [emFrente], R)).

Resources