_group(groups, fn) {
    var res = [];
    var map = Object.create(null);

    for (let i = 0; i < groups.length; i++) {
      for (let j = 0; j < groups[i].length; j++) {
        let id = fn(groups[i][j]);
        if (!map[id]) {
          map[id] = [];
        }

        map[id].push(groups[i][j]);
      }

      for (let key in map) {
        res.push(map[key]);
      }

      map = Object.create(null);
    }

    return res;
  }
Accepts a multi-dimensional array of nodes and groups them based on the
supplied function, which is expected to return a string.

@private

@param   {Node[][][]} groups The groups of nodes to further group
@param   {function}   fn     Synchronous function for generating group ids
@returns {Node[][][]}