Skip to content

Instantly share code, notes, and snippets.

@repeatedly
Created October 4, 2014 11:52
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save repeatedly/c4a0352c3ec322446e49 to your computer and use it in GitHub Desktop.
Save repeatedly/c4a0352c3ec322446e49 to your computer and use it in GitHub Desktop.
yajl-d, std.json, vibe.data.json comparison
import yajl;
import vibe.data.serialization;
import vibe.data.json;
import std.datetime;
import std.stdio;
import std.json;
import std.traits, std.typecons;
static struct Handa
{
static struct AAA
{
bool ok;
}
ulong id;
string name;
double height;
Nullable!AAA aaa;
}
void main()
{
immutable Num = 10000;
Handa handa;
handa.id = 1000;
handa.name = "shinobu";
handa.height = 169.5;
handa.aaa = Handa.AAA(true);
writeln("encode:");
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
toJSON(toJSONValue(handa));
}
sw.stop();
writefln("json: %s QPS", Num / sw.peek().to!("seconds", real));
}
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
serializeToJsonString(handa);
}
sw.stop();
writefln("vibe: %s QPS", Num / sw.peek().to!("seconds", real));
}
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
encode(handa);
}
sw.stop();
writefln("yajl: %s QPS", Num / sw.peek().to!("seconds", real));
}
writeln("decode:");
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
parseJSON(`{"id":1000,"name":"shinobu","height":169.5}`);
}
sw.stop();
writefln("json: %s QPS", Num / sw.peek().to!("seconds", real));
}
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
parseJsonString(`{"id":1000,"name":"shinobu","height":169.5}`);
}
sw.stop();
writefln("vibe: %s QPS", Num / sw.peek().to!("seconds", real));
}
{
auto sw = StopWatch(AutoStart.yes);
foreach (i; 0..Num) {
decode(`{"id":1000,"name":"shinobu","height":169.5}`);
}
sw.stop();
writefln("yajl: %s QPS", Num / sw.peek().to!("seconds", real));
}
}
@trusted
{
string toJSON(const JSONValue value)
{
return toJSON(value);
}
string toJSON(ref const JSONValue value)
{
return std.json.toJSON(&value);
}
}
@trusted
JSONValue toJSONValue(T)(auto ref T value)
{
JSONValue result;
static if (isTuple!T)
{
JSONValue[] arr;
foreach (i, Type; T.Types)
arr ~= value[i].toJSONValue();
result = arr;
}
else static if (is(T == struct) || is(T == class))
{
static if (is(T == class))
{
if (value is null) {
result = null;
return result;
}
}
JSONValue[string] obj;
foreach(i, v; value.tupleof) {
static if (isNullable!(typeof(v)))
{
if (!v.isNull)
obj[getFieldName!(T, i)] = v.get.toJSONValue();
}
else
{
obj[getFieldName!(T, i)] = v.toJSONValue();
}
}
result = obj;
}
else
{
result = value;
}
return result;
}
private template getFieldName(Type, size_t i)
{
static assert((is(Type == class) || is(Type == struct)), "Type must be class or struct: type = " ~ Type.stringof);
static assert(i < Type.tupleof.length, text(Type.stringof, " has ", Type.tupleof.length, " attributes: given index = ", i));
enum getFieldName = __traits(identifier, Type.tupleof[i]);
}
template isNullable(N)
{
static if(is(N == Nullable!(T), T) ||
is(N == NullableRef!(T), T) ||
is(N == Nullable!(T, nV), T, alias nV) &&
is(typeof(nV) == T))
{
enum isNullable = true;
}
else
{
enum isNullable = false;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment