I have the mathematical expression |z - (-1)| < 1, with z element of Complexes, which is equivalent of a circle of radius 1 centered in (x,y)=(-1,0).
How can I plot this expression,
preserving the structure of the mathematical expression it was derived from, as much as
possible?
It should be an area.
What I tried so far:
using ImplicitEquations, Plots
f(a,b) = abs.(a+im*b - (-1))
plot(f<1)
The error I got:
ERROR: MethodError: no method matching isless(::typeof(f), ::Int64)
Closest candidates are:
isless(::Union{StatsBase.PValue, StatsBase.TestStat}, ::Real) at /home/buddhilw/.julia/packages/StatsBase/PGTj8/src/statmodels.jl:514
isless(::AbstractGray{T} where T, ::Real) at /home/buddhilw/.julia/packages/ColorTypes/6m8P7/src/operations.jl:31
isless(::ForwardDiff.Dual{Tx, V, N} where {V, N}, ::Integer) where
Tx at /home/buddhilw/.julia/packages/ForwardDiff/UDrkY/src/dual.jl:144
...
Stacktrace:
[1] <(x::Function, y::Int64)
# Base ./operators.jl:279
[2] top-level scope
# REPL[62]:1
There's not a lot of documentation for ImplicitEquations, but something stands out: you're not using the right operators. The package relies on unusual operators to represent math expressions with Julia functions: ≪ (\ll[tab]), ≦ (\leqq[tab]), ⩵ (\Equal[tab]), ≶ (\lessgtr[tab]) or ≷ (\gtrless[tab]), ≧ (\geqq[tab]), ≫ (\leqq[tab]).
So that fix would look like:
using ImplicitEquations, Plots
f(a,b) = sqrt((a+1)^2 + b^2)
plot(f ≪ 1)
Update:
f(a,b) = abs(a + im*b - (-1)) causes a method ambiguity error. f(a, b) = hypot(a+1, b), which is what abs calls, also causes the error. It looks like the issue is that at some point in hypot, OInterval(x::Ointerval) is called, but dispatch could not pick between (::Type{T})(x::T) where T<:Number in boot.jl or OInterval(a) in intervals.jl. Just redefining OInterval(a::Ointerval) = a won't work either because you run into another MethodError for decompose(::OInterval), which is a method intended for processing floats. Looking at the comments in intervals.jl, the dispatch seems like a work in progress.
I'm trying to multiply two numbers in Prolog recursively i.e. 3*4 = 3+3+3+3 = 12.
My code is :
mult(0,Y,Y).
mult(X,Y,Z) :-
NewX is X-1,
Z is Y + mult(NewX,Y,Z).
but I keep either in an infinite loop or being told mult is not a function.
What you here constructed is a predicate. A predicate is not the same as a function in computer science, you can not write A is B + some_pred(C), or at least not as far as I know in ISO Prolog, and definitely not without adding some extra logic.
In order to pass values, one uses variables. We can thus call the mult/3 predicate recursively, and use a variable that will be unified with the result. We can then perform arithmetic with it, like:
mult(0, _, 0).
mult(X, Y, Z) :-
X1 is X - 1,
mult(X1, Y, Z1),
Z is Y + Z1.
Note that you can not reassign a (different) value to a variable. So if, like you did in the question, use Z twice, then given Y is not 0, this will fail.
The above is however still not sufficient, since it will produce a result, but then get stuck in an infinite loop since if it calls (eventually) mult(0, 4, Z) (4 is here just a value), there are two ways to resolve this: with the base case, and with the recursive case.
We thus need a "guard" for the second case, like:
mult(0, _, 0).
mult(X, Y, Z) :-
X > 0,
X1 is X - 1,
mult(X1, Y, Z1),
Z is Y + Z1.
We then obtain for example:
?- mult(14, 25, Z).
Z = 350 ;
false.
One can improve the speed of this mult/3 predicate by implementing a version with an accumulator. I leave this as an exercise.
This is exercise 3.5 from Learn Prolog Now. They put it before explaining lists so I need a procedure that doesn't involve lists.
The task is to swap the leaves of nested binary trees. If the query is
swap(tree(tree(leaf(1), leaf(2)), leaf(4)), T).
the answer should be
T = (tree(leaf(4), tree(leaf(2), leaf(1))).
With
swap((X, Y), (Y, X)).
swap(tree(X, Y), T) :-
swap((X, Y), (Y, X)),
T = (Y, X).
I get
T = (leaf(4), tree(leaf(1), leaf(2))).
As you see the leaf(1) and leaf(2) didn't get swapped. I want some hints or even your procedure and it should work with any depth of the nodes. Thanks.
You have a base case swap a leaf, and a general case swap a tree!
For a leaf, nothing to do :
swap(leaf(X), leaf(X)).
When you swap a tree, you must swap its leaves too, so
swap(tree(X,Y), tree(Y1,X1)) :-
swap(X,X1),
swap(Y,Y1).
The context, first. What I am trying to modelate with prolog are two separated graphs, both represent a group of friends, so in both of them I can put the relation friend(X,Y), and, because it's doesn't have sense the friendship isn't mutual in this model, I also put the relation friend(Y, X).
So this means that both graphs have bidirectional relationships between their elements.
For example:
friend(foo1, foo2).
friend(foo2, foo1).
friend(foo3, foo4).
friend(foo4, foo3).
In which foo1 is related with foo2, and the same goes for foo3 and foo4, but the first two are not related with the another two ones.
Because it is a group of friends, it also doesn´t have sense that in the same group of friends, two people of the same group aren't friends, so I am using recursion to determine if one person is friend of another.
definitivefriend(X, Z) :- friend(X, Z).
definitivefriend(X, Z) :- friend(X, Y), definitivefriend(Y, Z).
The problem I have is when I try to check if one person of one group is friend of a person of the other group. In other words, check if one element of of a graph is related with another element of the other graph.
Instead of getting false, which is the expected result, the compiler (SWI-Prolog, in this case), gives me an error of out of local stack.
I want to know how to solve this.
Edit
So thanks to CapelliC I have an approach of this problem. Because the main objective is complete, but there's a secondary problem I will describe it from now on.
These are the two graphs I am working with. Remember that I said before, both graphs are biredirectional.
Here's my program in prolog:
writeit :- write('Frienship').
definitivefriend(X, Z) :- friend(X, Z), friend(Z, X).
definitivefriend(X, Y) :- friend(X, Z), X #< Z, definitivefriend(Z, Y), Y \= X.
friend(amanda, ryan). % graph1 %
friend(ryan, amanda).
friend(ryan, lisa).
friend(lisa, ryan).
friend(bryan, ryan).
friend(ryan, bryan).
friend(sara, ryan).
friend(ryan, sara).
friend(sara, simone).
friend(simone, sara). % graph2 %
friend(sandra, jeff).
friend(jeff, sandra).
friend(betty, jeff).
friend(jeff, betty).
friend(jeff, antonia).
friend(antonia, jeff).
friend(jeff, oskar).
friend(oskar, jeff).
friend(jeff, leslie).
friend(leslie, jeff).
And here is some of the outputs I got
?- definitivefriend(amanda, ryan).
true . % It's correct, both nodes are neighbours %
?- definitivefriend(amanda, simone).
true . % It's correct, both nodes are in the same graph %
?- definitivefriend(ryan, simone).
true . % It's correct, same explanation as before %
?- definitivefriend(simone, amanda).
false. % It's wrong, expected result is true %
?- definitivefriend(ryan, jeff).
false. % It's correct, nodes are in different graphs %
?- definitivefriend(amanda, leslie).
false. % It's correct, same explanation as before %
?- definitivefriend(sandra, oskar).
false. % It's wrong, expected result is true %
?- definitivefriend(oskar, sandra).
false. % It's wrong, expected result is true %
?- definitivefriend(betty, oskar).
true . % It's correct, both nodes are in the same graph %
?- definitivefriend(oskar, betty).
false. % It's wrong, expected result is true %
As I said in the comments, even with some elements of the same graph (excepting the neighbour ones), definitivefriend gives me false. And are some cases when I execute definitivefriend(X, Y) I get true, but when I execite definitivefriend(Y, X) I get false.
I feel that you are not modelling in the right way, anyway this seems working (abusing of the suggestion by Jean-Bernard, +1)
definitivefriend(X, Y) :-
friend(X, Y),
friend(Y, X).
definitivefriend(X, Y) :-
friend(X, Z), X #< Z,
definitivefriend(Z, Y), Y \= X.
edit: this cannot work with your model. I can't see any other way than following Daniel suggestion (+1).
For your second definitivefriend rule, add a condition that X < Y. This will avoid cycles. Then simply add a rule for:
definitivefriend(X,Y) :- definitivefriend(Y,X)
As it is now, you could have:
definitivefriend(1,2) :- friend(1,3), definitivefriend(3,2)
definitivefriend(3,2) :- friend(2,1), definitivefriend(1,2)
Which leads to infinite recursion
The problem, basically, is cycles. Your graph is acyclic, but your code is not. Here's the question. Suppose I give the query :- definitivefriend(foo1, foo2).. What's to stop Prolog from expanding that like this:
definitivefriend(foo1, foo2)
:- friend(foo1, foo2), definitivefriend(foo2, foo2). % by clause 2
:- friend(foo1, foo2), friend(foo2, foo1), definitivefriend(foo1, foo2). % by clause 2
:- friend(foo1, foo2), friend(foo2, foo1), friend(foo1, foo2),
definitivefriend(foo2, foo2). % by clause 2
etc.
#Jean-Bernard Pellerin provides one useful way to prevent cycles, by forcing a total ordering. I don't think that's the right approach here, but I can't quite put my finger on why. However, one thing you can do is provide a visited list to check against and not re-enter nodes you've already been to. That code's going to look like this:
definitivefriend(X, Z) :- definitivefriend(X, Z, [X]).
definitivefriend(X, Y, Visited) :-
friend(X, Y), \+ memberchk(Y, Visited).
definitivefriend(X, Z, Visited) :-
friend(X, Y), \+ memberchk(Y, Visited),
definitivefriend(Y, Z, [Y|Visited]).
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.