The GitHub Actions job "Fury CI" on incubator-fury.git has succeeded.
Run started by GitHub user chaokunyang (triggered by chaokunyang).

Head commit for run:
6a0a07bb973a60d6589604af0c3e54fdcf1ae83d / weipeng <wangweip...@apache.org>
feat(JavaScript): xlang map code generator (#1571)

## What does this PR do?
Implement the code generator for Map. The code generator will produce
JavaScript code based on type descriptions at runtime. The generated
code is entirely inlined to minimize the number of function calls and
reduce the possibility of IC (Inline Cache) misses.

## Input type
```
Type.map(Type.string(), Type.string())
```

## Output Code
```JavaScript
function (fury, external) {
  const br = fury.binaryReader;
  const bw = fury.binaryWriter;
  const cr = fury.classResolver;
  const rr = fury.referenceResolver;

  const readInner = (fromRef) => {

    let count_0 = br.varInt32();
    const result_1 = new Map();
    if (fromRef) {
      rr.reference(result_1)
    }
    while (count_0 > 0) {
      const header = br.uint16();
      const keyHeader = header >> 12;
      const valueHeader = (header >> 8) & 0b00001111;
      const chunkSize = header & 0b11111111;
      br.skip(4);
      const keyIncludeNone = keyHeader & 2;
      const keyTrackingRef = keyHeader & 1;
      const valueIncludeNone = valueHeader & 2;
      const valueTrackingRef = valueHeader & 1;

      for (let index = 0; index < chunkSize; index++) {
        let key;
        let value;
        let flag = 0;
        if (keyTrackingRef || keyIncludeNone) {
          flag = br.uint8();
        }
        switch (flag) {
          case 0:
            key = br.stringOfVarUInt32()
            break;
          case -2:
            key = rr.getReadObject(br.varInt32())
            break;
          case -3:
            key = null;
            break;
          case -1:
            key = br.stringOfVarUInt32()
            break;
        }
        flag = 0;
        if (valueTrackingRef || valueIncludeNone) {
          flag = br.uint8();
        }
        switch (flag) {
          case 0:
            value = br.stringOfVarUInt32()
            break;
          case -2:
            value = rr.getReadObject(br.varInt32())
            break;
          case -3:
            value = null;
            break;
          case -1:
            value = br.stringOfVarUInt32()
            break;
        }
        result_1.set(
          key,
          value
        );
        count_0--;
      }
    }
    return result_1

  };
  const read = () => {

    const refFlag_2 = br.int8();
    switch (refFlag_2) {
      case -1:
      case 0:
        if (br.int16() === 256) {
          cr.readTag(br);
        }
        return readInner(refFlag_2 === 0)
      case -2:
        return rr.getReadObject(br.varUInt32())
      case -3:
        return null
    }

  };
  const writeInner = (v) => {

    bw.varInt32(v.size)
    let lastKeyIsNull_5 = false;
    let lastValueIsNull_6 = false;
    let chunkSize_7 = 0;
    let chunkSizeOffset_8 = 0;

    for (const [k_3, v_4] of v.entries()) {
      let keyIsNull = k_3 === null || k_3 === undefined;
      let valueIsNull = v_4 === null || v_4 === undefined;

      if (lastKeyIsNull_5 !== keyIsNull || lastValueIsNull_6 !== valueIsNull || 
chunkSize_7 === 0 || chunkSize_7 === 255) {
        if (chunkSize_7 > 0) {
          bw.setUint8Position(chunkSizeOffset_8, chunkSize_7);
          chunkSize_7 = 0;
        }
        chunkSizeOffset_8 = bw.getCursor()
        bw.uint16(((0 & (keyIsNull ? 2 : 0)) << 4) | (0 & (valueIsNull ? 2 : 
0)) << 8)
        bw.uint32(3084);

        lastKeyIsNull_5 = keyIsNull;
        lastValueIsNull_6 = valueIsNull;
      }
      if (keyIsNull) {
        bw.uint8(-3)
      }

      bw.stringOfVarUInt32(k_3)

      if (valueIsNull) {
        bw.uint8(-3)
      }

      bw.stringOfVarUInt32(v_4)

      chunkSize_7++;
    }
    if (chunkSize_7 > 0) {
      bw.setUint8Position(chunkSizeOffset_8, chunkSize_7);
    }

  };
  const write = (v) => {

    if (v !== null && v !== undefined) {
      bw.int24(4351);

      writeInner(v);
    } else {
      bw.int8(-3);
    }
  };

  return {
    read,
    readInner,
    write,
    writeInner,
    meta: { "fixedSize": 7, "needToWriteRef": false, "type": 15, "typeId": 16 }
  };
}
```

## Benchmark
## benchmark/map.js

We can notice that it isn't much faster than any serializer, because
iterating a Map is too expensive. But it is still necessary.

| (index)         | Values |
|-----------------|--------|
| any serialize   | 215    |
| any deserialize | 144    |
| jit serialize   | 291    |
| jit deserialize | 150    |
<!--
When the PR has an impact on performance (if you don't know whether the
PR will have an impact on performance, you can submit the PR first, and
if it will have impact on performance, the code reviewer will explain
it), be sure to attach a benchmark data here.
-->

Report URL: https://github.com/apache/incubator-fury/actions/runs/8834721684

With regards,
GitHub Actions via GitBox


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscr...@fury.apache.org
For additional commands, e-mail: commits-h...@fury.apache.org

Reply via email to