Contents

Description

The task here is to swap symbols in a sequence with their defined complements. One often finds this presented as a problem in e.g. “RNA transcription.”

For this one needs a way to pair complementary data values and look up a complementary value in either direction. The simple approach used here is to pair an object containing key-value pairs with the same object “mirrored.”

My solution

1. Mirror an object

In the mirrored object, each value in the original object is now a key, and each key in the original object is now a value.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
/**
 * Mirror an object.
 *
 * @param  {Object} obj - An object.
 * @return {Object} An object mirroring key-value pairs of the input object.
 *
 * @example
 * > mirror({'Z': 'A', 'Y': 'B'})
 * { A: 'Z', B: 'Y' }
 */
const mirror = obj =>
    Object.keys(obj).reduce((acc, curr) => {
        acc[obj[curr]] = curr;
        return acc;
    }, {});

2. Reversible look-up

Together, the original object and the mirrored object permit “reversible” look-up via short-circuit evaluation.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
/**
 * Swap each symbol in a string with its complement.
 *
 * @param {string} str - An input string.
 * @param {Object} compls - An object defining symbols and their complements.
 * @return {string} The input string's complement.
 *
 * @example
 * > const compls = {'A': 'T', 'C': 'G'}
 * > strCompl('ATTGC', compls)
 * 'TAACG'
 */
const strCompl = (str, compls) =>
    [...str]
    .map(char => compls[char] || mirror(compls)[char])
    .join('');

Tests

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
const assert = require('assert');


describe('mirror()', function() {
    it("should return a correctly mirrored object", function () {
        const obj = {'A': 'Z', 'B': 'Y'};
        assert.deepEqual(mirror(obj), {'Z': 'A', 'Y': 'B'});
    });
});


describe('strCompl()', function () {
    it('should swap symbols with their complements', function () {
        const compls = {'A': 'T', 'C': 'G'};
        assert.equal(strCompl('ATTGC', compls), 'TAACG')
    });
});