Created
March 23, 2024 05:52
-
-
Save ufcpp/94ee3c95fa2c000fbd57035fe5078974 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
unsafe | |
{ | |
Circle circle = new() { Radius = 1 }; | |
Rectangle rectangle = new() { Width = 2, Height = 3 }; | |
Rectangle square = new() { Width = 2, Height = 2 }; | |
Console.WriteLine(Algorithm.AreaRatio(0, &circle)); | |
Console.WriteLine(Algorithm.AreaRatio(1, &rectangle)); | |
Console.WriteLine(Algorithm.AreaRatio(1, &square)); | |
} | |
public struct Circle | |
{ | |
public double Radius; | |
} | |
struct Rectangle | |
{ | |
public double Width; | |
public double Height; | |
} | |
unsafe class Algorithm | |
{ | |
public static double AreaRatio(int vtableIndex, void* shape) | |
{ | |
return RuntimeTimeInfo.Vtables[vtableIndex].Area(shape) | |
/ RuntimeTimeInfo.Vtables[vtableIndex].Perimeter(shape); | |
} | |
} | |
unsafe class RuntimeTimeInfo | |
{ | |
public struct ShapeVTable | |
{ | |
public string Name; | |
public delegate*<void*, double> Area; | |
public delegate*<void*, double> Perimeter; | |
} | |
public static ShapeVTable[] Vtables = | |
[ | |
new() | |
{ | |
Name = "Circle", | |
Area = Func<Circle, double>(&Area), | |
Perimeter = Func<Circle, double>(&Perimeter), | |
}, | |
new() | |
{ | |
Name = "Rectangle", | |
Area = Func<Rectangle, double>(&Area), | |
Perimeter = Func<Rectangle, double>(&Perimeter), | |
} | |
]; | |
static delegate*<void*, TResult> Func<TThis, TResult>(delegate*<TThis*, TResult> @delegate) where TThis : unmanaged | |
{ | |
return (delegate*<void*, TResult>)@delegate; | |
} | |
static double Area(Circle* c) | |
{ | |
return Math.PI * c->Radius * c->Radius; | |
} | |
static double Perimeter(Circle* c) | |
{ | |
return 2 * Math.PI * c->Radius; | |
} | |
static double Area(Rectangle* r) | |
{ | |
return r->Width * r->Height; | |
} | |
static double Perimeter(Rectangle* r) | |
{ | |
return 2 * (r->Width + r->Height); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment