C
C#7d ago
Nanior

Calling static method of interface via it's type

There's an interface called ISerializer. ISerializer implements two static methods called Serialize and Deserialize. There's a class that implements ISerializer called ArraySerializer. ArraySerializer is requires an generic type parameter of type ISerializer... The ArraySerializer needs to call the Serialize/Deserialize method of the generic type parameter
34 Replies
Nanior
NaniorOP7d ago
What bugs me is that I know that the Type implements ISerializable, why can't I use the static methods of it?
c#
public class ArraySerializer<T, TSerializer> : ISerializer<T[]> where TSerializer : ISerializer<T>
{
public static void Deserialize(Stream stream, out T[] value)
{
value = new T[BitConverter.ToInt32(stream.Read(sizeof(int)))];
for (int i = 0; i < value.Length; i++)
{
value[i] = TSerializer.Deserialize()
}
}

public static void Serialize(Stream stream, T[] value)
{
stream.Write(BitConverter.GetBytes(value.Length));
}
}
c#
public class ArraySerializer<T, TSerializer> : ISerializer<T[]> where TSerializer : ISerializer<T>
{
public static void Deserialize(Stream stream, out T[] value)
{
value = new T[BitConverter.ToInt32(stream.Read(sizeof(int)))];
for (int i = 0; i < value.Length; i++)
{
value[i] = TSerializer.Deserialize()
}
}

public static void Serialize(Stream stream, T[] value)
{
stream.Write(BitConverter.GetBytes(value.Length));
}
}
sibber
sibber7d ago
what type implements ISerializable?
blueberriesiftheywerecats
Where T : ISerializer<T> Or if your type itself can't be a serializer, then just create an instance of TSerializer
sibber
sibber7d ago
this is all static here which yeah isnt a very good idea but whatever what do you expect TSerializer.Deserialize() to do?
Nanior
NaniorOP7d ago
Deserialize is a method that reads from a stream and returns something of Type T, that's what ISerializer is meant for (ISerializer is custom, not to be mistaken with whatever other interface that might be named the same) Unfortunately turns out it doesn't quite work the way I intended, particularly the part about static methods not being reference-able via the type Might have to completely rethink how this is supposed to work...
sibber
sibber7d ago
yeah but youre not giving it any arguments
Nanior
NaniorOP7d ago
I'm not giving it any arguments because look like it does not exist... Basically apparently you can't normally call a static method by the type That's why I'm asking, because I might need to step back and comepletely rethink the whole system, cus looks like my original plan is invalid in multiple ways How would you write something like this? It's meant to be used for saving primarily, converting binary from and to other types
sibber
sibber7d ago
im not sure what youre asking
MODiX
MODiX7d ago
sibber
REPL Result: Success
Print<Test>();

void Print<T>() where T : ITest
{
Console.WriteLine(T.Get());
}

interface ITest
{
static abstract int Get();
}

class Test : ITest
{
public static int Get() => 5;
}
Print<Test>();

void Print<T>() where T : ITest
{
Console.WriteLine(T.Get());
}

interface ITest
{
static abstract int Get();
}

class Test : ITest
{
public static int Get() => 5;
}
Console Output
5
5
Compile: 420.469ms | Execution: 74.448ms | React with ❌ to remove this embed.
sibber
sibber7d ago
thats valid
MODiX
MODiX7d ago
sibber
REPL Result: Success
return ArraySerializer<int, IntSerializer>.Deserialize();

interface ISerializer<T>
{
static abstract T Deserialize();
}

class IntSerializer : ISerializer<int>
{
public static int Deserialize() => 5;
}

class ArraySerializer<T, TSerializer> : ISerializer<T[]>
where TSerializer : ISerializer<T>
{
public static T[] Deserialize()
{
var arr = new T[3];
for (int i = 0; i < arr.Length; i++)
{
arr[i] = TSerializer.Deserialize();
}

return arr;
}
}
return ArraySerializer<int, IntSerializer>.Deserialize();

interface ISerializer<T>
{
static abstract T Deserialize();
}

class IntSerializer : ISerializer<int>
{
public static int Deserialize() => 5;
}

class ArraySerializer<T, TSerializer> : ISerializer<T[]>
where TSerializer : ISerializer<T>
{
public static T[] Deserialize()
{
var arr = new T[3];
for (int i = 0; i < arr.Length; i++)
{
arr[i] = TSerializer.Deserialize();
}

return arr;
}
}
Result: int[]
[
5,
5,
5
]
[
5,
5,
5
]
Compile: 428.780ms | Execution: 43.170ms | React with ❌ to remove this embed.
sibber
sibber7d ago
i think youre trying to do something like this? what isnt working for you?
Nanior
NaniorOP7d ago
Huh... Idk why it's working for you... Sure didn't when I did it? Is it Unity's C# version or something?
sibber
sibber7d ago
oh unity yeah it uses an old version, thats not supported
Nanior
NaniorOP7d ago
Back in mine, static interface methods must have a body, yours doesn't
sibber
sibber7d ago
did unity upgrdae to a newer version or something? static interface methods are fairly new iirc anyway you need to declare them abstract in the interface btw there are many serialization libraries so theres no need to do this for something other than learning
Nanior
NaniorOP7d ago
MessagePack always breaks badly, somehow I originally struggled with MessagePack a lot to get it to work in the first place
sibber
sibber7d ago
breaks how trying to fix it would be easier than writing your own
Nanior
NaniorOP7d ago
Later I struggled with it for days again when trying IL2CPP for potentially faster runtime And now it's when I tried migrating to Unity6
sibber
sibber7d ago
theres also MemoryPack which doesnt do encoding
Nanior
NaniorOP7d ago
Typically resolver issues, something about revolver not defined in standard resolver, or entirely not found And turned out later that I'd need to use .NET framework instead, because for some reason it didn't wanna work normally when on .NET standard I can't access the project right now so I can't tell what exactly the issue is anymore Um... Idk that package, can try I guess MessagePack is said to be very fast and compact, that's why I used it, but maybe it's not a robust design or something, idk, it just frequently ends up in trouble, mostly issues with custom type resolvers
sibber
sibber7d ago
ive never used it before personally, but its very popular and seems fairly battle tested so it must be robust it does look somewhat tricky to use in some cases tho tradeoff for performance MemoryPack is made by the same person
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
Nanior
NaniorOP7d ago
O.o Well, I had another look at MessagePack's documentation, and I see something I can try next time I work on my project... Might be that for some reason Unity6 doesn't automatically register the generated resolver like when I was trying IL2CPP, so I'll need to include the registry function At least, it sounds like it makes sense When my brother was trying to fix it he insisted that the only solution is to use .NET framework instead, which is why I decided to avoid MessagePack and try write my own
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
sibber
sibber7d ago
but for a game save file how would this happen
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
sibber
sibber7d ago
thats not really a volunrability you can say that about any format
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
sibber
sibber7d ago
it seems to just dump the raw bytes no encoding so the goal is performance if i understood correctly at least
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
sibber
sibber7d ago
oh i dont think they meant cross lang
Unknown User
Unknown User7d ago
Message Not Public
Sign In & Join Server To View
sibber
sibber7d ago
anyway yeah protobuf seems nice for that
Want results from more Discord servers?
Add your server