docs: private static void createList(List<ComponentList> listList,
        Map<MtasSpanQuery, Map<Integer, Integer>> spansNumberData,
        Map<MtasSpanQuery, Map<Integer, List<Match>>> spansMatchData,
        List<Integer> docSet, String field, int docBase, String uniqueKeyField,
        CodecInfo mtasCodecInfo, IndexSearcher searcher) throws IOException {
      if (listList != null) {
        for (ComponentList list : listList) {
          // collect not only stats
          if (list.number > 0) {
            Map<Integer, List<Match>> matchData = spansMatchData
                .get(list.spanQuery);
            Map<Integer, Integer> numberData = spansNumberData
                .get(list.spanQuery);
            List<Match> matchList;
            Integer matchNumber;
            if (list.output.equals(ComponentList.LIST_OUTPUT_HIT)) {
              for (int docId : docSet) {
                if (matchData != null
                    && (matchList = matchData.get(docId)) != null) {
                  if (list.position < (list.start + list.number)) {
                    boolean getDoc = false;
                    Match m;
                    for (int i = 0; i < matchList.size(); i++) {
                      if ((list.position >= list.start)
                          && (list.position < (list.start + list.number))) {
                        m = matchList.get(i);
                        getDoc = true;
                        int startPosition = m.startPosition;
                        int endPosition = m.endPosition - 1;
                        List<MtasTreeHit<String>> terms = mtasCodecInfo
                            .getPositionedTermsByPrefixesAndPositionRange(field,
                                (docId - docBase), list.prefixes,
                                startPosition - list.left,
                                endPosition + list.right);
                        // construct hit
                        Map<Integer, List<String>> kwicListHits = new HashMap<>();
                        for (int position = Math.max(0,
                            startPosition - list.left); position <= (endPosition
                                + list.right); position++) {
                          kwicListHits.put(position, new ArrayList<String>());
                        }
                        List<String> termList;
                        for (MtasTreeHit<String> term : terms) {
                          for (int position = Math.max(
                              (startPosition - list.left),
                              term.startPosition); position <= Math.min(
                                  (endPosition + list.right),
                                  term.endPosition); position++) {
                            termList = kwicListHits.get(position);
                            termList.add(term.data);
                          }
                        }
                        list.hits.add(new ListHit(docId, i, m, kwicListHits));
                      }
                      list.position++;
                    }
                    if (getDoc) {
                      // get unique id
                      Document doc = searcher.doc(docId,
                          new HashSet<String>(Arrays.asList(uniqueKeyField)));
                      IndexableField indxfld = doc.getField(uniqueKeyField);
                      // get other doc info
                      if (indxfld != null) {
                        list.uniqueKey.put(docId, indxfld.stringValue());
                      }
                      list.subTotal.put(docId, matchList.size());
                      IndexDoc mDoc = mtasCodecInfo.getDoc(field,
                          (docId - docBase));
                      if (mDoc != null) {
                        list.minPosition.put(docId, mDoc.minPosition);
                        list.maxPosition.put(docId, mDoc.maxPosition);
                      }
                    }
                  } else {
                    list.position += matchList.size();
                  }
                } else if (numberData != null
                    && (matchNumber = numberData.get(docId)) != null) {
                  list.position += matchNumber;
                }
              }
              list.total = list.position;
            } else if (list.output.equals(ComponentList.LIST_OUTPUT_TOKEN)) {
              for (int docId : docSet) {
                if (matchData != null
                    && (matchList = matchData.get(docId)) != null) {
                  if (list.position < (list.start + list.number)) {
                    boolean getDoc = false;
                    Match m;
                    for (int i = 0; i < matchList.size(); i++) {
                      if ((list.position >= list.start)
                          && (list.position < (list.start + list.number))) {
                        m = matchList.get(i);
                        getDoc = true;
                        int startPosition = m.startPosition;
                        int endPosition = m.endPosition - 1;
                        List<MtasTokenString> tokens;
                        tokens = mtasCodecInfo
                            .getPrefixFilteredObjectsByPositions(field,
                                (docId - docBase), list.prefixes,
                                startPosition - list.left,
                                endPosition + list.right);
                        list.tokens.add(new ListToken(docId, i, m, tokens));
                      }
                      list.position++;
                    }
                    if (getDoc) {
                      // get unique id
                      Document doc = searcher.doc(docId,
                          new HashSet<String>(Arrays.asList(uniqueKeyField)));
                      IndexableField indxfld = doc.getField(uniqueKeyField);
                      // get other doc info
                      if (indxfld != null) {
                        list.uniqueKey.put(docId, indxfld.stringValue());
                      }
                      list.subTotal.put(docId, matchList.size());
                      IndexDoc mDoc = mtasCodecInfo.getDoc(field,
                          (docId - docBase));
                      if (mDoc != null) {
                        list.minPosition.put(docId, mDoc.minPosition);
                        list.maxPosition.put(docId, mDoc.maxPosition);
                      }
                    }
                  } else {
                    list.position += matchList.size();
                  }
                } else if (numberData != null
                    && (matchNumber = numberData.get(docId)) != null) {
                  list.position += matchNumber;
                }
              }
              list.total = list.position;
            }
  
          } else {
            Map<Integer, Integer> data = spansNumberData.get(list.spanQuery);
            if (data != null) {
              for (int docId : docSet) {
                Integer matchNumber = data.get(docId);
                if (matchNumber != null) {
                  list.position += matchNumber;
                }
              }
              list.total = list.position;
            }
          }
        }
      }
    }