|
|
Comments and Discussions
|
|
 |

|
// test
JSON.Instance.toJSON(new { list = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, }.Where(i => i % 2 == 0) });
Line 329: foreach (var p in g)
Line 330: {
Line 331: object o = p.getter(obj); Line 332: if ((o == null || o is DBNull) && _params.serializeNullValues == false)
Line 333: {
// fix JosnSerializer.cs writeValue function.
else if (obj is IEnumerable)
|
|
|
|

|
Thanks!
The unit test pass ok, I will put this in the next release.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Hi again,
Not sure if this is a bug but I found that in my case, fastJson (latest) was not deserializing the data serialized by WCF DataContractSerializer. Maybe I have missed something?
We have a website using NewtonSoftJson. This is "called into" by external websites(one .Net 3.5 SP1 and one .Net 4.0) via cookies which happen to use WCF DataContractSerializer for serialializations.
In my tests where the serializer/deserializer were fastJson, all was good. So I had replaced NewtonSoftJson in our project with fastJson. That's when I saw that the data coming in from these external apps was not being de-serialized correctly by fastJson.
The data structure is as follows:
public class XYZ
{
public const string cookieName = "dummy";
[DataMember(Name = "f1")]
public string f1 { get; set; }
[DataMember(Name = "f6Url")]
public string f6Url{ get; set; }
[DataMember(Name = "f7")]
public string f7{ get; set; }
[DataMember(Name = "f8")]
public string f8{ get; set; }
[DataMember(Name = "f9")]
public string f9{ get; set; }
[DataMember(Name = "fBool")]
public string fBool{ get; set; }
public string f17Url{ get; set; }
}
Sorry, I could not create a test project. When I reverted back to either WCF DataContractSerializer or NewtonSoftJson, all was good again. I am sure I might have missed something. Any thoughts?
|
|
|
|

|
Hard to say without seeing the actual json and the code snippet you are using, try posting them and I will let you know.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I have some json strings with more fields than what I need. I'd like to end up with the same json strings, but with some of the fields removed.
Is there a way to deserialize to an object, then re-serialize and exclude some of the fields? Or is there a more performant way of doing this?
Also, is this page the best place to come for documentation or is there official documentation somewhere? Please forgive me if it's listed, I couldn't find it.
|
|
|
|

|
You can use the XmlIgnore attribute on your property and fields.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Do you have support for dynamic objects in fastJSON? It greatly helps in coding, especially when porting jscript to c#.
|
|
|
|

|
In a statically compiled language like c# you probably know the json format you are using, so you would define container classes in c# for them, so dynamic objects are not really needed.
If you don't know the json format then you can use Parse() which will give you a Dictionary structure of the json.
The general answer is no, dynamic objects are not supported (and it does not exist in .net v2).
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Thanks for your clarification.
And for my part I didn't notice the Parse() method. Nevertheless, many other implementations have already brought it to their code. So, don't you think that would be a good feature? Just a suggestion, nothing else!
|
|
|
|

|
Having free time is wonderful, when you have it!
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Good job there. I am trying to use this for nested classes that I have. In the sample below, it does not de-serialize what it has serialized. It is not able to create the object back after de-serialization. Why would that be?
class Program1
{
public class container
{
public string DataType;
public string Data;
}
public class setting
{
public Dictionary<string, string> basicCollection;
public string extraData;
}
public static void Main(string[] args)
{
setting s = new setting() { basicCollection = new Dictionary<string, string>(), extraData = "extra data value" };
s.basicCollection["key1"] = "value1";
s.basicCollection["key2"] = "value2";
container c = new container();
c.DataType = typeof(setting).ToString();
c.Data = fastJSON.JSON.Instance.ToJSON(s);
string serializedC = fastJSON.JSON.Instance.ToJSON(c);
container c1 = fastJSON.JSON.Instance.ToObject<container>(serializedC); Type t1 = Type.GetType(c1.DataType);
setting s1 = (setting)fastJSON.JSON.Instance.ToObject(c1.Data);
}
}
|
|
|
|

|
Thanks!
Your problem is that fastJSON does not have access to the type (must be public) so the easy fix is :
public class Program1 {
public class container
{
public string DataType;
public string Data;
}
...
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|
|

|
Good job on the article. Haven't looked at the code, but I'm intrigued. I've written some xml serializers before so I'm interested to checkout your code for JSON.
But I don't know what Stacks is? Can you provide a link? And yes, I've googled and found some promising links but I'm unsure if it's what you're referring to.
Thanks.
If your actions inspire others to dream more, learn more, do more and become more, you are a leader.-John Q. Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering.-Wernher von Braun Only two things are infinite, the universe and human stupidity, and I'm not sure about the former.-Albert Einstein
|
|
|
|

|
Thanks Ahmed!
If you mean ServiceStacks then the link is in the article, and it is a json/csv serializer.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I was referring to the performance table where you list "Stacks". ServiceStacks is what I found when I googled "JSON stacks".
Where is the "$type" and other "special" keywords documented for the JSON "standard".
If your actions inspire others to dream more, learn more, do more and become more, you are a leader.-John Q. Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering.-Wernher von Braun Only two things are infinite, the universe and human stupidity, and I'm not sure about the former.-Albert Einstein
|
|
|
|

|
Ah! I abbreviated the name in the excel sheets, but it is referring to ServiceStacks.
$type is not part of the JSON standard, it is an extension first used by JSON.net which kind of stuck. $types and $map are my extensions, and normally you would not need to work with them as they are handled internally.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
ok, thanks for the info.
Cheers!
If your actions inspire others to dream more, learn more, do more and become more, you are a leader.-John Q. Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering.-Wernher von Braun Only two things are infinite, the universe and human stupidity, and I'm not sure about the former.-Albert Einstein
|
|
|
|

|
Have you done any comparisons of using LINQ Expressions for generating your getters/setters code instead of using ILGenerator (which also requires the code using it to have elevated security privileges too if I'm not mistaken, where LINQ doesn't). Eg, I used LINQ Expressions to create accessors for private members, which you can see in this article[^]. I'd figure this would also allow the VM to optimize it since it's the one generating the IL from your high level expressions.
Also, why is 'myPropInfo' implemented as a struct (value type)? Not counting alignment padding, the structure is going has consume almost 50 bytes on a 32-bit platform (could be lessened with a Flags enum, but that still doesn't address my question about why it's a struct).
Every time you add or query an myPropInfo from your _propertycache, by definition the item retrieved should be a by-value copy of the stored 'myPropInfo', instead of a reference to. That just seems wasteful in terms of memory and execution performance, but if you have evidence to counter this assumption I'd like to see it (just as you've shown with all your other perf comparisons ).
edit: Also, wouldn't it be a tad more efficient to implement your CreateLong(string) method with an index and count parameter? In CreateDateTime you do a couple of value.Substring() calls. I would figure that you could just lose the extra string allocation from Substring and instead operating on the string's characters using its indexer instead of working on an enumerator.
It may also be better to have CreateInteger(out int/long num, string...) variants, at least for 32-bit platforms. Just to get rid of the extraneous 64-bit operations when you're dealing with ints (32-bits) in CreateDateTime (at least).
edit2: Looking more at the myPropInfo code, you have booleans for conditions which would be better suited in a 'type' Enum. Eg, isGuid vs isLong. A probably will only ever be one of those. Then in your 'ParseDictionary' method you could instead have a switch() statement that works on this hypothetical 'type' Enum's member for most of the if/else conditions, which would probably result in faster condition execution (assuming the JIT compiler generates an actual switch table in the assembly code)
edit3: I notice in some places you perform StringBuilder.Append calls on 1 character strings, instead of say an actual character (_output.Append("-") vs _output.Append('-')). Looking at the StringBuilder implementation for Append(string) and Append(char), it may prove to be slightly faster to use the char overload. While the string overload optimizes for strings which have 2 or less characters (and when there's enough free characters to append them), you would probably save a few cycles with the char overload due to fewer operations being done before the character is Append'ed
See for yourself:
public unsafe StringBuilder Append(string value)
{
if (value != null)
{
char[] chunkChars = this.m_ChunkChars;
int chunkLength = this.m_ChunkLength;
int length = value.Length;
int num3 = chunkLength + length;
if (num3 < chunkChars.Length)
{
if (length <= 0x2)
{
if (length > 0x0)
{
chunkChars[chunkLength] = value[0x0];
public StringBuilder Append(char value)
{
if (this.m_ChunkLength < this.m_ChunkChars.Length)
{
this.m_ChunkChars[this.m_ChunkLength++] = value;
}
else
{
this.Append(value, 0x1);
}
modified 13 Apr '13 - 20:25.
|
|
|
|

|
Thanks!
A couple of points:
1) fastJSON was designed to work with .net2+ so using LINQ and lambdas was not an option at the time (these requirement might not be valid now, but just the same).
2) IL gen is bare metal, and I doubt that you can get faster.
3) myPropInfo is a struct because it was faster (don't ask me why! I leave that to people with more time than me to figure out )
4) fastJSON was again designed to be as simple and as fast as possible given technical limitations, and has been optimized to mere percentages (in my opinion) to the current design.
Please feel free to change the code and try out new things and let me know, you never know I could be wrong...
Cheers
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Thanks for the reply. I'll try and look into testing the changes and will report back if I find anything of interest
modified 15 Apr '13 - 13:04.
|
|
|
|

|
Please add new comments instead of editing old ones, since editing does not notify me via email to take a look so I will probably miss them unless I open the article page.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Sorry about that! Since there was no response yet I just edited the post (the usual etiquette on other forums with simpler natures). Didn't consider how it handled emails (or lack thereof) Here's what I added in the edit yesterday:
The following are results from
1) Restructuring myPropInfo to use one Enum type and flags member instead of an assortment of bool's. On my x64 machine (with AnyCPU) myPropInfo was originally 0x98 bytes. After grouping all reference fields together and using the type/flags setup it boiled down to 0x40 bytes. At this stage, changing it to a class didn't seem to impact performance good or bad.
2) Restructuring 'ParseDictionary' to primarily use a switch() table instead of a block of if/else conditions
3) Reimplementing CreateLong as a static CreateInteger which uses an out parameter to deduce the integer type (there are overloads for int and long, with CreateDateTime using the int overload) and with a string/char[] index/count parameters instead of foreach'ing over a string.
4) ParseNumber in JsonParser uses the above implementation, avoiding a 'new string' allocation when the number doesn't have a decimal
5) Going through JsonSerializer and changing all 1-character string Append() calls to Append(char) calls.
6) Reimplementing consoletest to use Stopwatch instead of DateTime
7) .NET 4, AnyCPU (machine is natively x64) release build (and outside a debugger)
e-dataset
fastjson serialize 70 52 52 52 53
fastjson deserialize 107 91 88 88 87
+dataset
fastjson serialize 334 324 327 328 324
fastjson deserialize 680 676 675 680 678
e-dataset
fastjson serialize 71 52 52 52 53
fastjson deserialize 107 89 89 91 88
+dataset
fastjson serialize 330 324 326 324 325
fastjson deserialize 677 703 694 694 699
e-dataset
fastjson serialize 70 52 52 54 54
fastjson deserialize 113 89 89 89 89
+dataset
fastjson serialize 328 328 324 325 325
fastjson deserialize 672 669 671 676 674
e-dataset
fastjson serialize 70 52 52 52 52
fastjson deserialize 112 90 91 90 90
+dataset
fastjson serialize 329 322 322 322 322
fastjson deserialize 678 681 678 672 669
Original code (Stopwatch modifications only)
e-dataset
fastjson serialize 70 53 53 52 52
fastjson deserialize 114 92 90 92 91
+dataset
fastjson serialize 338 337 338 338 340
fastjson deserialize 697 695 695 695 698
e-dataset
fastjson serialize 70 53 55 54 55
fastjson deserialize 114 91 90 91 92
+dataset
fastjson serialize 341 339 340 336 338
fastjson deserialize 697 698 695 694 695
e-dataset
fastjson serialize 70 52 52 52 53
fastjson deserialize 115 92 91 92 92
+dataset
fastjson serialize 337 337 336 335 340
fastjson deserialize 675 674 678 673 672
Overall, my changes saw a consistent performance increase in the deserialization process. For +dataset though, there's a pretty nice improvement in serialize, while -dataset remains pretty much the same.
I think I have a CodePlex account so I can work on getting a clone up with these changes if you'd like, so you can investigate further.
|
|
|
|

|
Very nice! send me a diff when you can so I can try things out.
I remember using a switch without any speedups a long time ago.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I put the unified diff from 2.0.13 up on pastebin http://pastebin.com/Y0uGjLSy[^]
I use tabs instead of spaces, so that may irk you. VS's "format document" should take care of that for you though
Also forgot to mention: Right now in your Debug builds the CUSTOMTYPE macro has a '-' before it. I assuming this was intentional to make the compiler ignore it, but to still keep the macro definition there?
Release builds don't have it, so my timings don't factor CUSTOMTYPE support in
|
|
|
|

|
Thanks I will check it out.
Yep the customtype is there as a placeholder and not enabled, release build should have it also, although debug build seems to be faster than release for some strange reason (checked a long time ago so I don't know if it is the same now).
Try running the unit tests with your changes to make sure things still work.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I just downloaded and installed NUnit to run the unit tests you have and I'm happy to report that I didn't break anything! All 34 tests ran without error
|
|
|
|

|
I noticed in fastBinary that you use const bytes instead of an enum for your token types. I wanted to see if going this route made any impact with my changes. The following are results from changing the myPropInfoType/Flags to const ints (.NET 4, AnyCPU on a 64bit machine, Release) . Diff here: http://pastebin.com/30faGq0u[^] (still includes my original changes)
const int:
e-dataset
fastjson serialize 71 53 54 53 53
fastjson deserialize 112 90 89 89 90
+dataset
fastjson serialize 327 338 333 327 325
fastjson deserialize 674 669 702 677 671
e-dataset
fastjson serialize 70 53 53 52 53
fastjson deserialize 113 90 89 90 89
+dataset
fastjson serialize 326 322 322 336 322
fastjson deserialize 675 700 669 673 670
e-dataset
fastjson serialize 73 53 57 58 52
fastjson deserialize 112 90 90 90 89
+dataset
fastjson serialize 321 320 321 318 322
fastjson deserialize 681 684 696 694 681
enum:
e-dataset
fastjson serialize 74 69 63 56 52
fastjson deserialize 138 103 91 108 90
+dataset
fastjson serialize 324 332 334 327 324
fastjson deserialize 677 682 675 688 675
e-dataset
fastjson serialize 73 53 56 52 53
fastjson deserialize 112 90 90 90 90
+dataset
fastjson serialize 327 324 320 319 323
fastjson deserialize 673 668 672 667 676
e-dataset
fastjson serialize 70 52 53 52 52
fastjson deserialize 111 89 90 89 91
+dataset
fastjson serialize 336 333 346 340 334
fastjson deserialize 678 675 685 683 674
There was no real consistent difference between the two. Which is good because I like enums. I would have got a little depressed if there was a performance hit in using them.
|
|
|
|

|
In fastBinaryJSON the TOKENS are used in the output so I can't change them to enum (performance hit in the conversion to output).
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
... take a look at the binary version here : fastBinaryJSON[^]
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Ah yes, completely forgot about your BSON version . Will do. Have you thought about combining them under one repo, or having BSON be a subrepo, while having something like a fastJSON.Core for the shared code (along with making some use of InternalsVisableToAttribute)? Briefly scanning the code I saw the myPropInfo struct again, so I'm going to go out on a limb and assume that most of the reflection utilities are copy&pasted to BSON. If someone wanted to use both for whatever reason (eg, a game dev who develops with text but then ships using binary), they would end up with more memory overhead as both JSON and BSON libs would be duplicating that reflection code/data (at the very least).
Your Helper class in BSON seems to duplicate the GetBytes/ToXxx functions from BitConverter. I realize that you provide byte swapping functionality, but have you done speed comparisons to see if re-implementing those functions was faster than calling BitConverter's? Well, yours doesn't do any contract verification (bytes != null, etc) like BitConverter so that probably shaves off some cycles.
|
|
|
|

|
Well it's not BSON but a binary JSON, and yes most of the helper code is for performance.
As for combining the libraries, this is certainly desirable from my stand point in maintaining them both but the problem is the users of fastJSON are probably web devs and don't need binary, and the only people who need them both are network protocol and storage users which are few and trying to combine them will probably introduce extra layers and slow things down (speculating here).
I use them both in RaptorDB and there I factor out the same files and only use one.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
While going through your consoletest project, I noticed that you use DateTime for timing. Using Stopwatch is more precise in both timing and control over where you're timing. Eg (using bin_deserialize, line 211):
var stopwatch = new Stopwatch();
for (int pp = 0; pp < tcount; pp++)
{
BinaryFormatter bf = new BinaryFormatter();
MemoryStream ms = new MemoryStream();
colclass deserializedStore = null;
stopwatch.Restart();
bf.Serialize(ms, c);
for (int i = 0; i < count; i++)
{
stopwatch.Stop(); ms.Seek(0L, SeekOrigin.Begin);
stopwatch.Start();
deserializedStore = (colclass)bf.Deserialize(ms);
}
stopwatch.Stop();
Console.Write("\t" + stopwatch.ElapsedMilliseconds);
Just for being efficient in the test code itself, I created the stopwatch before the loop body (it's a reference type, not value like DateTime). From there, I start/restart (calling Restart is the same as calling Start on a fresh stopwatch) it after non-interesting operations (the MemoryStream ctor, etc) then essentially pause the stopwatch while Seek executes. Granted, it still means part of the for() loop itself is being timed, but overall it's a much better representation of your, or a 'rival's, API.
edit: Not sure if you noticed this (though you do have the bin_* methods commented out in Main) but none of the classes in dataobjects.cs are marked with [Serializable] so the bin_* methods will throw exceptions.
modified 14 Apr '13 - 12:54.
|
|
|
|

|
Please send me your full name so I can credit you in the next release.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Hi
Could you update your benchmarks to either benchmark against the latest version of Json.NET or remove Json.NET from them all together.
Thanks
James
|
|
|
|

|
Certainly, I will run the tests as soon as possible.
Thanks James!
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I have a class defined with an overloaded [] operator...for example:
public int this[int iX, int iY] { get { return m_aiData[iX,iY]; } set { m_aiData[iX,iY] = value;} }
However, the serializer seems to have a problem with this, giving me the exception "Common Language Runtime detected an invalid program."
I tested a variety of scenarios and this fails on *any* property of this type, unless of course I remove the "set", since it becomes read-only in that case and is ignored by fastJSON.
Is there any way around this? Is this something that can't be serialized? Of course I can make the property read-only and create a seperate function to "set" the values, but I'd really prefer not to, if possible. Thanks!
Edit: I forgot it doesn't handle n-dimension array, so I'll have to change some stuff anway But, I'd still like to have a definite answer.
modified 28 Mar '13 - 16:46.
|
|
|
|

|
While I can't speak for Mehdi, I'm fairly certain this is because fastJSON doesn't handle multi-dimensional arrays.
As a quick solution, you could try writing a simpler POCO that is used for storage only, and then translate to/from this new class before and after doing (de)serialization.
|
|
|
|

|
Unfortunately fastJSON does not handle multi-dimensianal arrays i.e. int[,].
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
*edit* I got this to work using (Dictionary)Parse(json), but documentation doesn't seem to support that this is how it should be done. For now, I am satisfied, but there is room for improvement with ToObject()
Hi. I'm reposting my question from CodePlex as I realized it isn't a very popular forum to communicate to you.
I'm working on a localization project and would like to deserialize a json string to a Dictionary in which some of the values may be another Dictionary for size optimization purposes (essentially namespacing). An example of the json is below.
{
"app": {
"title": "TITLE_EN",
"desc": "DESC_EN",
"settings": {
"" : "SETTINGS_EN"
"title": "SETTINGS_TITLE_EN"
}
}
}
I plan to end up with something I can recurse through and flatten down into a less complex Dictionary.
Unfortunately, attempts at using fastJSON.JSON.Instance.ToObject>(json) results in an exception in mscorlib's Dictionary.cs. According to jsonlint.com the string is valid json.
I had success using Parse(json) and ToObject(json), but it insists upon nesting IList which is undesirable to me. Do you have any recommendations on how to achieve this with fastJSON? Thanks for your hard work on this project.
modified 21 Mar '13 - 14:30.
|
|
|
|

|
Is there a way to serialize a collection of unknown-type objects, and determine their original type after de-serialization?
EG: object[] toSerialize = new[]{ new Guid() };
If I serialize the above, the serialized form doesn't store the GUID's type, and the GUID is de-serialized into a string.
Is there a way around this? Do I have to use generics / Tuple to accomplish this?
|
|
|
|

|
Since json does not store type information and you only get strings and numbers, then no you can't.
fastJSON uses the type information from the class type you supply ($type property) for deserializtion.
You might want to look at my fastBinaryJSON project which overcomes this limitation.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
I hope you don't mind, but I created a fork of fastJSON:
https://github.com/kamranayub/fastJSON[^]
I added two features:
* RootElement support (it simply returns the first key match in the dictionary if present)
* Name variance (disabled by default)
I also organized the solution a bit because I had trouble getting everything running from your original source. I also pushed a Nuget package of my fork (different package name) so I could pull it into my project.
I separated the changes from the reorganization, so feel free to take a look at what I did. It would be great to see these updates in the core fastJSON! I just needed them right now.
|
|
|
|

|
Great job!
I might incorporate the property name variant override ( quite useful).
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
One of the nice features of some other deserializers (RestSharp) is the ability to pass in a "root element" so you don't need to deserialize into a container class:
{
"person": {
"name": "Kamran"
}
}
fastJSON.JSON.Instance.ToObject<Person>(json, rootElement: "person")
This would be very helpful for REST APIs (or any service). Some APIs have useful containers (error, status, etc.) but the one I'm dealing with right now just adds a containing element for the heck of it.
-Kamran Ayub
|
|
|
|

|
Thanks!
It's probably faster to deserialize the entire json and extract the item you want in code:
var o = fastJSON.JSON.Instance.ToObject<objecttype>(json);
var p = o.Person;
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Hi Mehdi,
first: thanks for fixing the problem with the edge case with nulls.
Now I run into the problem, that through a REST request I receive a Json string which is varies, depending on the request. The object contains a property for an id, which can contain one or more ids
- In case with one id, the property: is like "id": 123.
- In case of multiple ids, the property is: "id": "1234,12546,52344"
The problem is now: if only one id is passed (id=12) the parser throughs a cast error. The reason is, that fastJson uses a direct cast to convert the received object. Yet in the case of multiple values, the case is successful.
My question is now: why are you using a direct cast and not a ToString() method? With the ToString() method I can cover both scenarios.
Thanks for your input.
Chris
|
|
|
|

|
If id is a string then you shouldn't have a problem, but if it is an int then you can't put "1234,12345" in it.
Its the man, not the machine - Chuck Yeager
If at first you don't succeed... get a better publicist
If the final destination is death, then we should enjoy every second of the journey.
|
|
|
|

|
Would it be possible to update the version submitted to NuGet? It's 1.9.6 at the moment and you have fixed a number of bugs between then and now.
Kind thanks,
Roja
|
|
|
|

|
Concerning objects implementing IList or ICollection, all properties (other than items) are not serialized.
This snippet of serializer's code, seems to confirm this fact :
else if (obj is Array || obj is IList || obj is ICollection)
WriteArray((IEnumerable)obj);
Is it a normal behaviour ?
|
|
|
|
 |
|
|
General News Suggestion Question Bug Answer Joke Rant Admin
Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.
|
Smallest, fastest polymorphic JSON serializer (with Silverlight4 and MonoDroid support)
| Type | Article |
| Licence | CPOL |
| First Posted | 19 Feb 2011 |
| Views | 1,565,676 |
| Downloads | 26,037 |
| Bookmarked | 464 times |
|
|