Data commit

This commit is contained in:
Ingy döt Net 2023-07-01 11:58:00 -04:00
parent 7387c8f97b
commit cb5bb5e222
199093 changed files with 3378972 additions and 0 deletions

View file

@ -0,0 +1,21 @@
Option Explicit On
Option Infer On
Option Strict On
Module Currying
' The trivial curry.
Function Curry(Of T1, TResult)(func As Func(Of T1, TResult)) As Func(Of T1, TResult)
' At least satisfy the implicit contract that the result isn't reference-equal to the original function.
Return Function(a) func(a)
End Function
Function Curry(Of T1, T2, TResult)(func As Func(Of T1, T2, TResult)) As Func(Of T1, Func(Of T2, TResult))
Return Function(a) Function(b) func(a, b)
End Function
Function Curry(Of T1, T2, T3, TResult)(func As Func(Of T1, T2, T3, TResult)) As Func(Of T1, Func(Of T2, Func(Of T3, TResult)))
Return Function(a) Function(b) Function(c) func(a, b, c)
End Function
' And so on.
End Module

View file

@ -0,0 +1,29 @@
Module Main
' An example binary function.
Function Add(a As Integer, b As Integer) As Integer
Return a + b
End Function
Sub Main()
Dim curriedAdd = Curry(Of Integer, Integer, Integer)(AddressOf Add)
Dim add2To = curriedAdd(2)
Console.WriteLine(Add(2, 3))
Console.WriteLine(add2To(3))
Console.WriteLine(curriedAdd(2)(3))
' An example ternary function.
Dim substring = Function(s As String, startIndex As Integer, length As Integer) s.Substring(startIndex, length)
Dim curriedSubstring = Curry(substring)
Console.WriteLine(substring("abcdefg", 2, 3))
Console.WriteLine(curriedSubstring("abcdefg")(2)(3))
' The above is just syntax sugar for this (a call to the Invoke() method of System.Delegate):
Console.WriteLine(curriedSubstring.Invoke("abcdefg").Invoke(2).Invoke(3))
Dim substringStartingAt1 = curriedSubstring("abcdefg")(1)
Console.WriteLine(substringStartingAt1(2))
Console.WriteLine(substringStartingAt1(4))
End Sub
End Module

View file

@ -0,0 +1,51 @@
Option Explicit On
Option Infer On
Option Strict On
Module CurryingDynamic
' Cheat visual basic's syntax by defining a type that can be the receiver of what appears to be a method call.
' Needless to say, this is not idiomatic VB.
Class CurryDelegate
ReadOnly Property Value As Object
ReadOnly Property Target As [Delegate]
Sub New(value As Object)
Dim curry = TryCast(value, CurryDelegate)
If curry IsNot Nothing Then
Me.Value = curry.Value
Me.Target = curry.Target
ElseIf TypeOf value Is [Delegate] Then
Me.Target = DirectCast(value, [Delegate])
Else
Me.Value = value
End If
End Sub
' CurryDelegate could also work as a dynamic n-ary function delegate, if an additional ParamArray argument were to be added.
Default ReadOnly Property Invoke(arg As Object) As CurryDelegate
Get
If Me.Target Is Nothing Then Throw New InvalidOperationException("All curried parameters have already been supplied")
Return New CurryDelegate(Me.Target.DynamicInvoke({arg}))
End Get
End Property
' A syntactically natural way to assert that the currying is complete and that the result is of the specified type.
Function Unwrap(Of T)() As T
If Me.Target IsNot Nothing Then Throw New InvalidOperationException("Some curried parameters have not yet been supplied.")
Return DirectCast(Me.Value, T)
End Function
End Class
Function DynamicCurry(func As [Delegate]) As CurryDelegate
Return DynamicCurry(func, ImmutableList(Of Object).Empty)
End Function
' Use ImmutableList to create a new list every time any curried subfunction is called avoiding multiple or repeated
' calls interfering with each other.
Private Function DynamicCurry(func As [Delegate], collectedArgs As ImmutableList(Of Object)) As CurryDelegate
Return If(collectedArgs.Count = func.Method.GetParameters().Length,
New CurryDelegate(func.DynamicInvoke(collectedArgs.ToArray())),
New CurryDelegate(Function(arg As Object) DynamicCurry(func, collectedArgs.Add(arg))))
End Function
End Module

View file

@ -0,0 +1,27 @@
Module Program
Function Add(a As Integer, b As Integer) As Integer
Return a + b
End Function
Sub Main()
' A delegate for the function must be created in order to eagerly perform overload resolution.
Dim curriedAdd = DynamicCurry(New Func(Of Integer, Integer, Integer)(AddressOf Add))
Dim add2To = curriedAdd(2)
Console.WriteLine(add2To(3).Unwrap(Of Integer))
Console.WriteLine(curriedAdd(2)(3).Unwrap(Of Integer))
Dim substring = Function(s As String, i1 As Integer, i2 As Integer) s.Substring(i1, i2)
Dim curriedSubstring = DynamicCurry(substring)
Console.WriteLine(substring("abcdefg", 2, 3))
Console.WriteLine(curriedSubstring("abcdefg")(2)(3).Unwrap(Of String))
' The trickery of using a parameterized default property also makes it appear that the "delegate" has an Invoke() method.
Console.WriteLine(curriedSubstring.Invoke("abcdefg").Invoke(2).Invoke(3).Unwrap(Of String))
Dim substringStartingAt1 = curriedSubstring("abcdefg")(1)
Console.WriteLine(substringStartingAt1(2).Unwrap(Of String))
Console.WriteLine(substringStartingAt1(4).Unwrap(Of String))
End Sub
End Module