code: function decode(object, memo, path) {
          memo = memo || new Map();
          path = path || "";
          if (Object(object) !== object) {
              return object;
          } else if (object["$"] !== void 0) {
              return memo.get(object["$"]);
          } else if (object["%"]) {
              if (object["%"] === "undefined") {
                  return undefined;
              } else if (object["%"] === "+Infinity") {
                  return Number.POSITIVE_INFINITY;
              } else if (object["%"] === "-Infinity") {
                  return Number.NEGATIVE_INFINITY;
              } else if (object["%"] === "NaN") {
                  return Number.NaN;
              } else {
                  return Q.reject(new TypeError("Unrecognized type: " + object["%"]));
              }
          } else if (object["!"]) {
              return Q.reject(object["!"]);
          } else if (object["@r"]) {
              var remote = makeRemote(object["@r"]);
              if (object.type === "function") {
                  return function () {
                      return Q.fapply(remote, Array.prototype.slice.call(arguments));
                  };
              } else {
                  return remote;
              }
          } else if (object["@l"]) {
            return locals.get(object["@l"]);
          } else {
              var newObject = Array.isArray(object) ? [] : {};
              memo.set(path, newObject);
              for (var key in object) {
                  if (has.call(object, key)) {
                      var newKey = key.replace(/\\([\\!@%\$\/])/, function ($0, $1) {
                          return $1;
                      });
                      newObject[newKey] = decode(object[key], memo, path + "/" + key);
                  }
              }
              return newObject;
          }
      }
docs: decodes QSON