98 lines
2.5 KiB
Text
98 lines
2.5 KiB
Text
Const As Double INF = 1e30
|
|
|
|
Type Punto
|
|
As Double x, y
|
|
Declare Constructor (x As Double = INF, y As Double = INF)
|
|
Declare Function copy() As Punto
|
|
Declare Function isZero() As Integer
|
|
Declare Function neg() As Punto
|
|
Declare Function dbl() As Punto
|
|
Declare Function sum(q As Punto) As Punto
|
|
Declare Function mul(n As Integer) As Punto
|
|
Declare Function ToString() As String
|
|
End Type
|
|
|
|
Dim Shared As Integer bCoeff = 7 ' Coeficiente de la curva elíptica
|
|
|
|
Constructor Punto(x As Double, y As Double)
|
|
This.x = Iif(Abs(x) > 1e20, INF, x)
|
|
This.y = Iif(Abs(y) > 1e20, INF, y)
|
|
End Constructor
|
|
|
|
Function Punto.copy() As Punto
|
|
Return Type(This.x, This.y)
|
|
End Function
|
|
|
|
Function Punto.isZero() As Integer
|
|
Return This.x >= 1e20 Or This.x <= -1e20 Or This.x = INF
|
|
End Function
|
|
|
|
Function Punto.neg() As Punto
|
|
Return Type(This.x, -This.y)
|
|
End Function
|
|
|
|
Function Punto.dbl() As Punto
|
|
If This.isZero() Then Return This.copy()
|
|
|
|
If Abs(This.y) < 1e-15 Then Return Punto()
|
|
|
|
Dim As Double L = (3 * This.x * This.x) / (2 * This.y)
|
|
Dim As Double x3 = L * L - 2 * This.x
|
|
Return Type(x3, L * (This.x - x3) - This.y)
|
|
End Function
|
|
|
|
Function Punto.sum(q As Punto) As Punto
|
|
If This.x = q.x And This.y = q.y Then Return This.dbl()
|
|
If This.isZero() Then Return q.copy()
|
|
If q.isZero() Then Return This.copy()
|
|
|
|
If Abs(q.x - This.x) < 1e-15 Then Return Punto()
|
|
|
|
Dim As Double L = (q.y - This.y) / (q.x - This.x)
|
|
Dim As Double x3 = L * L - This.x - q.x
|
|
Return Type(x3, L * (This.x - x3) - This.y)
|
|
End Function
|
|
|
|
Function Punto.mul(n As Integer) As Punto
|
|
Dim As Punto r = Punto(), p = This.copy()
|
|
|
|
While n > 0
|
|
If (n And 1) Then r = r.sum(p)
|
|
p = p.dbl()
|
|
n = n Shr 1
|
|
Wend
|
|
Return r
|
|
End Function
|
|
|
|
Function Punto.ToString() As String
|
|
If This.isZero() Then Return "Zero"
|
|
Return "(" & Str(Int(This.x * 1000) / 1000) & ", " & Str(Int(This.y * 1000) / 1000) & ")"
|
|
End Function
|
|
|
|
Sub show(s As String, p As Punto)
|
|
Print s & " " & p.ToString()
|
|
End Sub
|
|
|
|
Function from_y(y As Double) As Punto
|
|
Dim As Double n = y * y - bCoeff
|
|
Dim As Double x = Sgn(n) * Abs(n)^(1.0/3.0)
|
|
Return Type(x, y)
|
|
End Function
|
|
|
|
' Demonstrate
|
|
Dim As Punto a = from_y(1)
|
|
Dim As Punto b = from_y(2)
|
|
show("a =", a)
|
|
show("b =", b)
|
|
|
|
Dim As Punto c = a.sum(b)
|
|
show("c = a + b =", c)
|
|
|
|
Dim As Punto d = c.neg()
|
|
show("d = -c =", d)
|
|
|
|
show("c + d =", c.sum(d))
|
|
show("a + b + d =", a.sum(b.sum(d)))
|
|
show("a * 12345 =", a.mul(12345))
|
|
|
|
Sleep
|