|
安装IJulia
使用using IJulia; notebook(dir="C:/Users/myself",detached=true) 打开Jupyter notebook
根据这里安装PyCall
A symbolic proof
将下面的命令粘贴到Cell, 按Shift+Enter执行:
引入SymPy- using Pkg;
- Pkg.activate(".");
- Pkg.add("SymPy")
- using SymPy
复制代码
定义一些基本的几何对象。
- import Base: isequal, ==
- abstract type GeoObject end
- abstract type GeoShape <: GeoObject end
- struct Point <: GeoObject
- x::Number
- y::Number
- end
- (==)(p1::Point, p2::Point) = p1.x==p2.x && p1.y==p2.y
- struct Triangle <: GeoShape
- A::Point
- B::Point
- C::Point
- end
- Triangle(ax, ay, bx, by, cx, cy) = Triangle(Point(ax, ay), Point(bx, by), Point(cx, cy))
- (==)(t1::Triangle, t2::Triangle) = vertices(t1) == vertices(t2)
- function vertices(tri::Triangle)
- [tri.A, tri.B, tri.C]
- end
- struct Edge <: GeoShape
- src::Point
- dst::Point
- end
- function edges(tri::Triangle)
- elist = Edge[]
- pts = vertices(tri)
- for i in 1:length(pts)-1
- push!(elist, Edge(pts[i], pts[i+1]))
- end
- push!(elist, Edge(pts[length(pts)], pts[1]))
- elist
- end
复制代码
计算两点距离的函数
- function squaredist(A, B)
- d = (A.x-B.x)^2+(A.y-B.y)^2
- if d isa Sym
- simplify(d)
- else
- d
- end
- end;
复制代码
计算三角形重心的函数
- function centroid(pts)
- Point(sum([[pt.x,pt.y] for pt in pts])/length(pts)...)
- end
复制代码
检查正三角形的函数
- function isequilateral(tri)
- dist = [squaredist(e.src, e.dst) for e in edges(tri)]
- if (dist[1] == dist[2]) && (dist[1] == dist[3])
- return true
- else
- return false
- end
- end
复制代码
给定两个点 A, B 解出点 P 使得 PA=PB=AB (这样的 P 有两个)
- function equipoints(A, B)
- x, y = @vars x y
- pt = Point(x, y)
- dist1 = squaredist(pt, A)
- dist2 = squaredist(pt, B)
- dist3 = squaredist(A, B)
- sol = solve([dist1-dist3, dist2-dist3], [x,y]) # Soving a quadratic eqaution.
- [Point(s[1], s[2]) for s in sol]
- end;
复制代码
我们在两个点 P 中选择到 C 较远的一个作为向外的等边三角形
- function outer_equitri(A, B, C)
- ptAB = equipoints(A, B)
- dist = map(pt->squaredist(pt, C), ptAB)
- d = simplify(dist[1] - dist[2])
- if d >= 0
- return Triangle(A, B, ptAB[1])
- else
- return Triangle(A, B, ptAB[2])
- end
- end;
复制代码
用A, B, C表示三角形顶点坐标
- @vars by cx positive=true;
- @vars cy;
- A = Point(0, 0); B = Point(0, by); C = Point(cx, cy);
- tri = Triangle(A, B, C)
复制代码
证明Napoleon定理
- function napoleon_check(tri)
- outer_tri = map(i->outer_equitri(circshift(vertices(tri), i)...), 0:2)
- centers = centroid.(vertices.(outer_tri));
- npt = Triangle(centers...)
- isequilateral(npt)
- end
- napoleon_check(tri)
复制代码
运行结果为true 
|
|