/** * @license * Copyright 2020 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ import * as tf from '../index'; import { ALL_ENVS, describeWithFlags } from '../jasmine_util'; import { expectArraysEqual } from '../test_util'; async function expectTensor(tensor, shape, value) { const length = shape.length === 0 ? 1 : shape.reduce((a, b) => a * b); expect(tensor.shape).toEqual(shape); expectArraysEqual(await tensor.data(), new Array(length).fill(value)); } describeWithFlags('squeeze', ALL_ENVS, () => { it('default', async () => { const assertType = async (dtype) => { const value = dtype === 'string' ? 'test' : 0.0; // Nothing to squeeze. await expectTensor(tf.squeeze(tf.fill([2], value)), [2], value); // Squeeze the middle element away. await expectTensor(tf.squeeze(tf.fill([2, 1, 2], value)), [2, 2], value); // Squeeze on both ends. await expectTensor(tf.squeeze(tf.fill([1, 2, 1, 3, 1], value)), [2, 3], value); }; await assertType('string'); await assertType('float32'); }); it('specific dimension', async () => { const assertType = async (dtype) => { const value = dtype === 'string' ? 'test' : 0.0; const shape = [1, 2, 1, 3, 1]; // Positive squeeze dim index. await expectTensor(tf.squeeze(tf.fill(shape, value), [0]), [2, 1, 3, 1], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [2, 4]), [1, 2, 3], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [0, 4, 2]), [2, 3], value); // Negative squeeze dim index. await expectTensor(tf.squeeze(tf.fill(shape, value), [-1]), [1, 2, 1, 3], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [-3, -5]), [2, 3, 1], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [-3, -5, -1]), [2, 3], value); }; await assertType('string'); await assertType('float32'); }); it('all ones', async () => { const assertType = async (dtype) => { const value = dtype === 'string' ? 'test' : 0.0; await expectTensor(tf.squeeze(tf.fill([1, 1, 1], value)), [], value); }; await assertType('string'); await assertType('float32'); }); it('squeeze only ones', async () => { const assertType = async (dtype) => { const value = dtype === 'string' ? 'test' : 0.0; const shape = [1, 1, 3]; await expectTensor(tf.squeeze(tf.fill(shape, value)), [3], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [0]), [1, 3], value); await expectTensor(tf.squeeze(tf.fill(shape, value), [1]), [1, 3], value); expect(() => tf.squeeze(tf.fill(shape, value), [2])).toThrowError(); }; await assertType('string'); await assertType('float32'); }); it('squeeze errors', async () => { const assertType = async (dtype) => { const value = dtype === 'string' ? 'test' : 0.0; const shape = [1, 2, 1]; expect(() => tf.squeeze(tf.fill(shape, value), [-4])).toThrowError(); expect(() => tf.squeeze(tf.fill(shape, value), [0, -4])).toThrowError(); expect(() => tf.squeeze(tf.fill(shape, value), [3])).toThrowError(); expect(() => tf.squeeze(tf.fill(shape, value), [2, 3])).toThrowError(); }; await assertType('string'); await assertType('float32'); }); }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic3F1ZWV6ZV90ZXN0LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vdGZqcy1jb3JlL3NyYy9vcHMvc3F1ZWV6ZV90ZXN0LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7Ozs7Ozs7Ozs7Ozs7R0FlRztBQUNILE9BQU8sS0FBSyxFQUFFLE1BQU0sVUFBVSxDQUFDO0FBQy9CLE9BQU8sRUFBQyxRQUFRLEVBQUUsaUJBQWlCLEVBQUMsTUFBTSxpQkFBaUIsQ0FBQztBQUM1RCxPQUFPLEVBQUMsaUJBQWlCLEVBQUMsTUFBTSxjQUFjLENBQUM7QUFFL0MsS0FBSyxVQUFVLFlBQVksQ0FDdkIsTUFBaUIsRUFBRSxLQUFlLEVBQUUsS0FBb0I7SUFDMUQsTUFBTSxNQUFNLEdBQUcsS0FBSyxDQUFDLE1BQU0sS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQztJQUN0RSxNQUFNLENBQUMsTUFBTSxDQUFDLEtBQUssQ0FBQyxDQUFDLE9BQU8sQ0FBQyxLQUFLLENBQUMsQ0FBQztJQUNwQyxpQkFBaUIsQ0FBQyxNQUFNLE1BQU0sQ0FBQyxJQUFJLEVBQUUsRUFBRSxJQUFJLEtBQUssQ0FBQyxNQUFNLENBQUMsQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQztBQUN4RSxDQUFDO0FBRUQsaUJBQWlCLENBQUMsU0FBUyxFQUFFLFFBQVEsRUFBRSxHQUFHLEVBQUU7SUFDMUMsRUFBRSxDQUFDLFNBQVMsRUFBRSxLQUFLLElBQUksRUFBRTtRQUN2QixNQUFNLFVBQVUsR0FBRyxLQUFLLEVBQUUsS0FBeUIsRUFBRSxFQUFFO1lBQ3JELE1BQU0sS0FBSyxHQUFHLEtBQUssS0FBSyxRQUFRLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxDQUFD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QUFDLEdBQUcsQ0FBQztZQUNoRCxNQUFNLEtBQUssR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUM7WUFDeEIsTUFBTSxZQUFZLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUM7WUFDbEUsTUFBTSxZQUFZLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUM7WUFDMUUsTUFBTSxZQUFZLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUM7WUFDMUUsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLEVBQUUsQ0FBQyxPQUFPLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsS0FBSyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsWUFBWSxFQUFFLENBQUM7UUFDdEUsQ0FBQyxDQUFDO1FBRUYsTUFBTSxVQUFVLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDM0IsTUFBTSxVQUFVLENBQUMsU0FBUyxDQUFDLENBQUM7SUFDOUIsQ0FBQyxDQUFDLENBQUM7SUFFSCxFQUFFLENBQUMsZ0JBQWdCLEVBQUUsS0FBSyxJQUFJLEVBQUU7UUFDOUIsTUFBTSxVQUFVLEdBQUcsS0FBSyxFQUFFLEtBQXlCLEVBQUUsRUFBRTtZQUNyRCxNQUFNLEtBQUssR0FBRyxLQUFLLEtBQUssUUFBUSxDQUFDLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQztZQUNoRCxNQUFNLEtBQUssR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUM7WUFDeEIsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLEVBQUUsQ0FBQyxPQUFPLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsS0FBSyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxZQUFZLEVBQUUsQ0FBQztZQUNyRSxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxZQUFZLEVBQUUsQ0FBQztZQUN4RSxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxZQUFZLEVBQUUsQ0FBQztZQUNwRSxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsWUFBWSxFQUFFLENBQUM7UUFDekUsQ0FBQyxDQUFDO1FBRUYsTUFBTSxVQUFVLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDM0IsTUFBTSxVQUFVLENBQUMsU0FBUyxDQUFDLENBQUM7SUFDOUIsQ0FBQyxDQUFDLENBQUM7QUFDTCxDQUFDLENBQUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8qKlxuICogQGxpY2Vuc2VcbiAqIENvcHlyaWdodCAyMDIwIEdvb2dsZSBMTEMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuXG4gKiBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgXCJMaWNlbnNlXCIpO1xuICogeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLlxuICogWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0XG4gKlxuICogaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wXG4gKlxuICogVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZVxuICogZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gXCJBUyBJU1wiIEJBU0lTLFxuICogV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuXG4gKiBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kXG4gKiBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS5cbiAqID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gKi9cbmltcG9ydCAqIGFzIHRmIGZyb20gJy4uL2luZGV4JztcbmltcG9ydCB7QUxMX0VOVlMsIGRlc2NyaWJlV2l0aEZsYWdzfSBmcm9tICcuLi9qYXNtaW5lX3V0aWwnO1xuaW1wb3J0IHtleHBlY3RBcnJheXNFcXVhbH0gZnJvbSAnLi4vdGVzdF91dGlsJztcblxuYXN5bmMgZnVuY3Rpb24gZXhwZWN0VGVuc29yKFxuICAgIHRlbnNvcjogdGYuVGVuc29yLCBzaGFwZTogbnVtYmVyW10sIHZhbHVlOiBzdHJpbmd8bnVtYmVyKSB7XG4gIGNvbnN0IGxlbmd0aCA9IHNoYXBlLmxlbmd0aCA9PT0gMCA/IDEgOiBzaGFwZS5yZWR1Y2UoKGEsIGIpID0+IGEgKiBiKTtcbiAgZXhwZWN0KHRlbnNvci5zaGFwZSkudG9FcXVhbChzaGFwZSk7XG4gIGV4cGVjdEFycmF5c0VxdWFsKGF3YWl0IHRlbnNvci5kYXRhKCksIG5ldyBBcnJheShsZW5ndGgpLmZpbGwodmFsdWUpKTtcbn1cblxuZGVzY3JpYmVXaXRoRmxhZ3MoJ3NxdWVlemUnLCBBTExfRU5WUywgKCkgPT4ge1xuICBpdCgnZGVmYXVsdCcsIGFzeW5jICgpID0+IHtcbiAgICBjb25zdCBhc3NlcnRUeXBlID0gYXN5bmMgKGR0eXBlOiAnc3RyaW5nJ3wnZmxvYXQzMicpID0+IHtcbiAgICAgIGNvbnN0IHZhbHVlID0gZHR5cGUgPT09ICdzdHJpbmcnID8gJ3Rlc3QnIDogMC4wO1xuICAgICAgLy8gTm90aGluZyB0byBzcXVlZXplLlxuICAgICAgYXdhaXQgZXhwZWN0VGVuc29yKHRmLnNxdWVlemUodGYuZmlsbChbMl0sIHZhbHVlKSksIFsyXSwgdmFsdWUpO1xuXG4gICAgICAvLyBTcXVlZXplIHRoZSBtaWRkbGUgZWxlbWVudCBhd2F5LlxuICAgICAgYXdhaXQgZXhwZWN0VGVuc29yKHRmLnNxdWVlemUodGYuZmlsbChbMiwgMSwgMl0sIHZhbHVlKSksIFsyLCAyXSwgdmFsdWUpO1xuXG4gICAgICAvLyBTcXVlZXplIG9uIGJvdGggZW5kcy5cbiAgICAgIGF3YWl0IGV4cGVjdFRlbnNvcihcbiAgICAgICAgICB0Zi5zcXVlZXplKHRmLmZpbGwoWzEsIDIsIDEsIDMsIDFdLCB2YWx1ZSkpLCBbMiwgM10sIHZhbHVlKTtcbiAgICB9O1xuXG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnc3RyaW5nJyk7XG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnZmxvYXQzMicpO1xuICB9KTtcblxuICBpdCgnc3BlY2lmaWMgZGltZW5zaW9uJywgYXN5bmMgKCkgPT4ge1xuICAgIGNvbnN0IGFzc2VydFR5cGUgPSBhc3luYyAoZHR5cGU6ICdzdHJpbmcnfCdmbG9hdDMyJykgPT4ge1xuICAgICAgY29uc3QgdmFsdWUgPSBkdHlwZSA9PT0gJ3N0cmluZycgPyAndGVzdCcgOiAwLjA7XG4gICAgICBjb25zdCBzaGFwZSA9IFsxLCAyLCAxLCAzLCAxXTtcbiAgICAgIC8vIFBvc2l0aXZlIHNxdWVlemUgZGltIGluZGV4LlxuICAgICAgYXdhaXQgZXhwZWN0VGVuc29yKFxuICAgICAgICAgIHRmLnNxdWVlemUodGYuZmlsbChzaGFwZSwgdmFsdWUpLCBbMF0pLCBbMiwgMSwgMywgMV0sIHZhbHVlKTtcbiAgICAgIGF3YWl0IGV4cGVjdFRlbnNvcihcbiAgICAgICAgICB0Zi5zcXVlZXplKHRmLmZpbGwoc2hhcGUsIHZhbHVlKSwgWzIsIDRdKSwgWzEsIDIsIDNdLCB2YWx1ZSk7XG4gICAgICBhd2FpdCBleHBlY3RUZW5zb3IoXG4gICAgICAgICAgdGYuc3F1ZWV6ZSh0Zi5maWxsKHNoYXBlLCB2YWx1ZSksIFswLCA0LCAyXSksIFsyLCAzXSwgdmFsdWUpO1xuXG4gICAgICAvLyBOZWdhdGl2ZSBzcXVlZXplIGRpbSBpbmRleC5cbiAgICAgIGF3YWl0IGV4cGVjdFRlbnNvcihcbiAgICAgICAgICB0Zi5zcXVlZXplKHRmLmZpbGwoc2hhcGUsIHZhbHVlKSwgWy0xXSksIFsxLCAyLCAxLCAzXSwgdmFsdWUpO1xuICAgICAgYXdhaXQgZXhwZWN0VGVuc29yKFxuICAgICAgICAgIHRmLnNxdWVlemUodGYuZmlsbChzaGFwZSwgdmFsdWUpLCBbLTMsIC01XSksIFsyLCAzLCAxXSwgdmFsdWUpO1xuICAgICAgYXdhaXQgZXhwZWN0VGVuc29yKFxuICAgICAgICAgIHRmLnNxdWVlemUodGYuZmlsbChzaGFwZSwgdmFsdWUpLCBbLTMsIC01LCAtMV0pLCBbMiwgM10sIHZhbHVlKTtcbiAgICB9O1xuXG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnc3RyaW5nJyk7XG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnZmxvYXQzMicpO1xuICB9KTtcblxuICBpdCgnYWxsIG9uZXMnLCBhc3luYyAoKSA9PiB7XG4gICAgY29uc3QgYXNzZXJ0VHlwZSA9IGFzeW5jIChkdHlwZTogJ3N0cmluZyd8J2Zsb2F0MzInKSA9PiB7XG4gICAgICBjb25zdCB2YWx1ZSA9IGR0eXBlID09PSAnc3RyaW5nJyA/ICd0ZXN0JyA6IDAuMDtcbiAgICAgIGF3YWl0IGV4cGVjdFRlbnNvcih0Zi5zcXVlZXplKHRmLmZpbGwoWzEsIDEsIDFdLCB2YWx1ZSkpLCBbXSwgdmFsdWUpO1xuICAgIH07XG5cbiAgICBhd2FpdCBhc3NlcnRUeXBlKCdzdHJpbmcnKTtcbiAgICBhd2FpdCBhc3NlcnRUeXBlKCdmbG9hdDMyJyk7XG4gIH0pO1xuXG4gIGl0KCdzcXVlZXplIG9ubHkgb25lcycsIGFzeW5jICgpID0+IHtcbiAgICBjb25zdCBhc3NlcnRUeXBlID0gYXN5bmMgKGR0eXBlOiAnc3RyaW5nJ3wnZmxvYXQzMicpID0+IHtcbiAgICAgIGNvbnN0IHZhbHVlID0gZHR5cGUgPT09ICdzdHJpbmcnID8gJ3Rlc3QnIDogMC4wO1xuICAgICAgY29uc3Qgc2hhcGUgPSBbMSwgMSwgM107XG4gICAgICBhd2FpdCBleHBlY3RUZW5zb3IodGYuc3F1ZWV6ZSh0Zi5maWxsKHNoYXBlLCB2YWx1ZSkpLCBbM10sIHZhbHVlKTtcbiAgICAgIGF3YWl0IGV4cGVjdFRlbnNvcih0Zi5zcXVlZXplKHRmLmZpbGwoc2hhcGUsIHZhbHVlKSwgWzBdKSwgWzEsIDNdLCB2YWx1ZSk7XG4gICAgICBhd2FpdCBleHBlY3RUZW5zb3IodGYuc3F1ZWV6ZSh0Zi5maWxsKHNoYXBlLCB2YWx1ZSksIFsxXSksIFsxLCAzXSwgdmFsdWUpO1xuICAgICAgZXhwZWN0KCgpID0+IHRmLnNxdWVlemUodGYuZmlsbChzaGFwZSwgdmFsdWUpLCBbMl0pKS50b1Rocm93RXJyb3IoKTtcbiAgICB9O1xuXG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnc3RyaW5nJyk7XG4gICAgYXdhaXQgYXNzZXJ0VHlwZSgnZmxvYXQzMicpO1xuICB9KTtcblxuICBpdCgnc3F1ZWV6ZSBlcnJvcnMnLCBhc3luYyAoKSA9PiB7XG4gICAgY29uc3QgYXNzZXJ0VHlwZSA9IGFzeW5jIChkdHlwZTogJ3N0cmluZyd8J2Zsb2F0MzInKSA9PiB7XG4gICAgICBjb25zdCB2YWx1ZSA9IGR0eXBlID09PSAnc3RyaW5nJyA/ICd0ZXN0JyA6IDAuMDtcbiAgICAgIGNvbnN0IHNoYXBlID0gWzEsIDIsIDFdO1xuICAgICAgZXhwZWN0KCgpID0+IHRmLnNxdWVlemUodGYuZmlsbChzaGFwZSwgdmFsdWUpLCBbLTRdKSkudG9UaHJvd0Vycm9yKCk7XG4gICAgICBleHBlY3QoKCkgPT4gdGYuc3F1ZWV6ZSh0Zi5maWxsKHNoYXBlLCB2YWx1ZSksIFswLCAtNF0pKS50b1Rocm93RXJyb3IoKTtcbiAgICAgIGV4cGVjdCgoKSA9PiB0Zi5zcXVlZXplKHRmLmZpbGwoc2hhcGUsIHZhbHVlKSwgWzNdKSkudG9UaHJvd0Vycm9yKCk7XG4gICAgICBleHBlY3QoKCkgPT4gdGYuc3F1ZWV6ZSh0Zi5maWxsKHNoYXBlLCB2YWx1ZSksIFsyLCAzXSkpLnRvVGhyb3dFcnJvcigpO1xuICAgIH07XG5cbiAgICBhd2FpdCBhc3NlcnRUeXBlKCdzdHJpbmcnKTtcbiAgICBhd2FpdCBhc3NlcnRUeXBlKCdmbG9hdDMyJyk7XG4gIH0pO1xufSk7XG4iXX0=