/**
   * Build a category dataset.
   *
   * @param tableBlock The table block to parse.
   * @param dataRange The data range.
   * @param datasetBuilder The dataset builder.
   * @throws MacroExecutionException if there are any errors.
   */
  private void buildDataset(
      TableBlock tableBlock, int[] dataRange, TableDatasetBuilder datasetBuilder)
      throws MacroExecutionException {
    int startRow = dataRange[0];
    int startColumn = dataRange[1];
    int endRow = dataRange[2];
    int endColumn = dataRange[3];

    if (startRow == 0 && datasetBuilder.forceRowHeadings()) {
      startRow = 1;
    }

    if (startColumn == 0 && datasetBuilder.forceColumnHeadings()) {
      startColumn = 1;
    }

    getRowKeys(tableBlock, startRow, endRow, startColumn, datasetBuilder);

    getColumnKeys(tableBlock, startColumn, endColumn, startRow, datasetBuilder);

    for (int i = startRow; i <= endRow; i++) {
      if (i < tableBlock.getChildren().size()) {
        TableRowBlock tableRow = (TableRowBlock) tableBlock.getChildren().get(i);
        for (int j = startColumn; j <= endColumn; j++) {
          if (j < tableRow.getChildren().size()) {
            Number value = cellContentAsNumber((TableCellBlock) tableRow.getChildren().get(j));
            datasetBuilder.setValue(i - startRow, j - startColumn, value);
          } else {
            throw new MacroExecutionException("Data range (columns) overflow.");
          }
        }
      } else {
        throw new MacroExecutionException("Data range (rows) overflow.");
      }
    }
  }