JSONKit v1.4 Release Notes
Release Date: 2011-03-23 // almost 14 years ago-
No data yet ๐
You can check the official repo
Previous changes from v1.3
-
๐ New Features
Added the
JK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
pre-processor define flag.This is typically enabled by adding
-DJK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
to the compilers command line arguments or inXcode.app
by addingJK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
to a projects / targetsPre-Processor Macros
settings.The
JK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
option enables the use of custom Core Foundation collection call backs which omit the [CFRetain
][CFRetain] calls. This results in saving several [CFRetain
][CFRetain] and [CFRelease
][CFRelease] calls typically needed for every single object from the parsed JSON. While the author has used this technique for years without any issues, an unexpected interaction with the Foundation [-mutableCopy
][-mutableCopy] method and Core Foundation Toll-Free Bridging resulting in a condition in which the objects contained in the collection to be over released. This problem does not occur with the use of [-copy
][-copy] due to the fact that the objects created by JSONKit are immutable, and therefore [-copy
][-copy] does not require creating a completely new object and copying the contents, instead [-copy
][-copy] simply returns a [-retain
][-retain]'d version of the immutable object which is significantly faster along with the obvious reduction in memory usage.Prior to version 1.3, JSONKit always used custom "Transfer of Ownership Collection Callbacks", and thus
JK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
was effectively implicitly defined.Beginning with version 1.3, the default behavior of JSONKit is to use the standard Core Foundation collection callbacks ([
kCFTypeArrayCallBacks
][kCFTypeArrayCallBacks], [kCFTypeDictionaryKeyCallBacks
][kCFTypeDictionaryKeyCallBacks], and [kCFTypeDictionaryValueCallBacks
][kCFTypeDictionaryValueCallBacks]). The intention is to follow "the principle of least surprise", and the author believes the use of the standard Core Foundation collection callbacks as the default behavior for JSONKit results in the least surprise.NOTE:
JK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
is only applicable to(CF|NS)
Dictionary
andArray
class objects.For the vast majority of users, the author believes JSONKits custom "Transfer of Ownership Collection Callbacks" will not cause any problems. As previously stated, the author has used this technique in performance critical code for years and has never had a problem. Until a user reported a problem with [
-mutableCopy
][-mutableCopy], the author was unaware that the use of the custom callbacks could even cause a problem. This is probably due to the fact that the vast majority of time the typical usage pattern tends to be "iterate the contents of the collection" and very rarely mutate the returned collection directly (although this last part is likely to vary significantly from programmer to programmer). The author tends to avoid the use of [-mutableCopy
][-mutableCopy] as it results in a significant performance and memory consumption penalty. The reason for this is in "typical" Cocoa coding patterns, using [-mutableCopy
][-mutableCopy] will instantiate an identical, albeit mutable, version of the original object. This requires both memory for the new object and time to iterate the contents of the original object and add them to the new object. Furthermore, under "typical" Cocoa coding patterns, the original collection object continues to consume memory until the autorelease pool is released. However, clearly there are cases where the use of [-mutableCopy
][-mutableCopy] makes sense or may be used by an external library which is out of your direct control.The use of the standard Core Foundation collection callbacks results in a 9% to 23% reduction in parsing performance, with an "eye-balled average" of around 13% according to some benchmarking done by the author using Real World™ JSON (i.e., actual JSON from various web services, such as Twitter, etc) using
gcc-4.2 -arch x86_64 -O3 -DNS_BLOCK_ASSERTIONS
with the only change being the addition of-DJK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
.JK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
is only applicable to parsing / deserializing (i.e. converting from) of JSON. Serializing (i.e., converting to JSON) is completely unaffected by this change.
๐ Bug Fixes
- Fixed a bug report regarding
-mutableCopy
. This is related to the addition of the pre-processor define flagJK_ENABLE_CF_TRANSFER_OWNERSHIP_CALLBACKS
.
Other Changes
- Added
JK_EXPECTED
optimization hints around several conditionals. - When serializing objects, JSONKit first starts with a small, on stack buffer. If the encoded JSON exceeds the size of the stack buffer, JSONKit switches to a heap allocated buffer. If JSONKit switched to a heap allocated buffer, [
CFDataCreateWithBytesNoCopy
][CFDataCreateWithBytesNoCopy] is used to create the [NSData
][NSData] object, which in most cases causes the heap allocated buffer to "transfer" to the [NSData
][NSData] object which is substantially faster than allocating a new buffer and copying the bytes. - ๐ Added a pre-processor check in
JSONKit.m
to see if Objective-C Garbage Collection is enabled and issue a#error
notice that JSONKit does not support Objective-C Garbage Collection. - โก๏ธ Various other minor or trivial modifications, such as updating
README.md
.
Other Issues
When using the
clang
static analyzer (the version used at the time of this writing wasApple clang version 1.5 (tags/Apple/clang-60)
), the static analyzer reports a number of problems withJSONKit.m
.The author has investigated these issues and determined that the problems reported by the current version of the static analyzer are "false positives". Not only that, the reported problems are not only "false positives", they are very clearly and obviously wrong. Therefore, the author has made the decision that no action will be taken on these non-problems, which includes not modifying the code for the sole purpose of silencing the static analyzer. The justification for this is "the dog wags the tail, not the other way around."