Hi,
I came across an interesting issue and wanted to share it. We had a scenario where a deserialization using BinaryFormatter from .net 4.0 to .net 3.5 (CLR2.0) raise an exception which contains the following classes:
EnumEqualityComparer,
InvalidCastException,
And the following error messages as well:
"Object Must Implement IConvertible"
"Cannot load type 'System.Collections.Generic.EumEqualityComparer`1...'
I found a solution for this and I would like to explain it with an example:
Suppose you have an enum:
enum TileSize
{
Big = 1,
Medium = 2,
Small = 3
}
and you have a code where you are using a dictionary:
IDictionary<TileSize, int> items = new Dictionary<TileSize, int>();
items.Add(TileSize.Big, 20); //we have 20 tiles of size big.
items.Add(TileSize.Small, 10); //we have 10 tiles of size small.
Now, if you have a client/server environment where you have got .net 4.0 server and a .net 3.5 (CLR 2.0) client.
when you will try to serialize this items object using BinaryFormatter, it will serialize perfectly fine but on deserialization on the client side you will encounter error explaining "Object Must Implement IConvertible" and also you will see the following error on client:
"Cannot load type 'System.Collections.Generic.EumEqualityComparer`1...'
Why I get this error?
The class EnumEqualityComparer is internally used in .NET 4.0 and it is new to CLR2.0.
When the class TileSize is serialized, The BinaryFormatter in .NET 4.0 uses EnumEqualityComparer to serialize and deserialize an Enum whereas the earlier frameworks use System.Collection.Generic.ObjectEqualityComparer.
How to fix?
An easiest way to fix this issue is to place a base type other than integer, for an enum, like the following:
enum TileSize : byte
{
Big = 1,
Medium = 2,
Small = 3
}
When we put an 'non int' base type for an enum, the BinaryFormatter of .NET 4.0 uses ObjectEqualityComparer instead of EnumEqualityComparer. And the object easily gets deserialized on lower version of .NET Framework.
I think the article is very simple and helpful. Still if you have any question, please feel free to comment.
Regards
Kajal
I came across an interesting issue and wanted to share it. We had a scenario where a deserialization using BinaryFormatter from .net 4.0 to .net 3.5 (CLR2.0) raise an exception which contains the following classes:
EnumEqualityComparer,
InvalidCastException,
And the following error messages as well:
"Object Must Implement IConvertible"
"Cannot load type 'System.Collections.Generic.EumEqualityComparer`1...'
I found a solution for this and I would like to explain it with an example:
Suppose you have an enum:
enum TileSize
{
Big = 1,
Medium = 2,
Small = 3
}
and you have a code where you are using a dictionary:
IDictionary<TileSize, int> items = new Dictionary<TileSize, int>();
items.Add(TileSize.Big, 20); //we have 20 tiles of size big.
items.Add(TileSize.Small, 10); //we have 10 tiles of size small.
Now, if you have a client/server environment where you have got .net 4.0 server and a .net 3.5 (CLR 2.0) client.
when you will try to serialize this items object using BinaryFormatter, it will serialize perfectly fine but on deserialization on the client side you will encounter error explaining "Object Must Implement IConvertible" and also you will see the following error on client:
"Cannot load type 'System.Collections.Generic.EumEqualityComparer`1...'
Why I get this error?
The class EnumEqualityComparer is internally used in .NET 4.0 and it is new to CLR2.0.
When the class TileSize is serialized, The BinaryFormatter in .NET 4.0 uses EnumEqualityComparer to serialize and deserialize an Enum whereas the earlier frameworks use System.Collection.Generic.ObjectEqualityComparer.
How to fix?
An easiest way to fix this issue is to place a base type other than integer, for an enum, like the following:
enum TileSize : byte
{
Big = 1,
Medium = 2,
Small = 3
}
When we put an 'non int' base type for an enum, the BinaryFormatter of .NET 4.0 uses ObjectEqualityComparer instead of EnumEqualityComparer. And the object easily gets deserialized on lower version of .NET Framework.
I think the article is very simple and helpful. Still if you have any question, please feel free to comment.
Regards
Kajal
Cool solution! You had prevent me from wasting time trying to find out the solution.
ReplyDeleteYou saved us from going insane trying to figure this out. Thanks!
ReplyDeleteThank you so much for this simple solution!
ReplyDeletecool man thanks
ReplyDeleteI'm having the same issue, except our customers are using our application compiled against 4.5 .NET framework. Recently someone installed Windows 10 which uses .NET 4.6. During deserialization, I get the same exception you listed in your example; "Cannot load type 'System.Collections.Generic.EumEqualityComparer`1. " I tried adding the 'byte' to my int enum, but it didn't seem to make a difference.
ReplyDeleteIronically, .NET 4.4 and 4.6 both use the EumEqualityComparer during serialization. I can't figure out what I need to change so our customers can open their project files in Windows 10.
any other ideas will be appreciated.
thank you
Also, please contact me via email if you have any ideas...
ReplyDeletegcadmes@gmail.com
thanks