dsmiley commented on a change in pull request #1310: SOLR-13350: Multithreaded search using collector managers URL: https://github.com/apache/lucene-solr/pull/1310#discussion_r397858537
########## File path: solr/core/src/java/org/apache/solr/search/SolrIndexSearcher.java ########## @@ -1643,6 +1660,83 @@ public ScoreMode scoreMode() { qr.setDocList(new DocSlice(0, sliceLen, ids, scores, totalHits, maxScore)); } + CollectorManagerResult searchCollectorManagers(int len, QueryCommand cmd, Query query, + boolean needTopDocs, boolean needMaxScore, boolean needDocSet) throws IOException { + CollectorManager<MultiCollector, CollectorManagerResult> manager = new CollectorManager<MultiCollector, CollectorManagerResult>() { + @Override + public MultiCollector newCollector() throws IOException { + // nocommit: Here, creating a MultiCollector for every segment (correctness > speed). + // Need to explore sharing a single MultiCollector with every segment. Are these + // sub-collectors thread-safe? DocSetCollector seems like not thread-safe, does someone know? + Collection<Collector> collectors = new ArrayList<Collector>(); + if (needTopDocs) collectors.add(buildTopDocsCollector(len, cmd)); + if (needMaxScore) collectors.add(new MaxScoreCollector()); + if (needDocSet) collectors.add(new DocSetCollector(maxDoc())); + return (MultiCollector) MultiCollector.wrap(collectors); + } + + @Override + public CollectorManagerResult reduce(Collection<MultiCollector> multiCollectors) throws IOException { + final TopDocs[] topDocs = new TopDocs[multiCollectors.size()]; + float maxScore = 0.0f; + DocSet docSet = new BitDocSet(new FixedBitSet(maxDoc())); // TODO: if docset is not needed, avoid this initialization + int i = 0; + for (MultiCollector multiCollector: multiCollectors) { + int c = 0; + List<Collector> subCollectors = multiCollector.getCollectors(); + TopDocsCollector topDocsCollector = needTopDocs? ((TopDocsCollector) subCollectors.get(c++)): null; + MaxScoreCollector maxScoreCollector = needMaxScore? ((MaxScoreCollector) subCollectors.get(c++)): null; + DocSetCollector docSetCollector = needDocSet? ((DocSetCollector) subCollectors.get(c++)): null; + + if (needTopDocs) topDocs[i++] = (topDocsCollector instanceof TopFieldCollector)? ((TopFieldCollector)topDocsCollector).topDocs(0, len): topDocsCollector.topDocs(0, len); + if (needMaxScore) + if (!Float.isNaN(maxScoreCollector.getMaxScore())) + maxScore = Math.max(maxScore, maxScoreCollector.getMaxScore()); + if (needDocSet) docSet = docSet.union(docSetCollector.getDocSet()); + } + TopDocs mergedTopDocs; + if (topDocs != null && topDocs.length>0 && topDocs[0] instanceof TopFieldDocs) { + TopFieldDocs[] topFieldDocs = Arrays.copyOf(topDocs, topDocs.length, TopFieldDocs[].class); + mergedTopDocs = TopFieldDocs.merge(weightSort(cmd.getSort()), len, topFieldDocs); + } else { + mergedTopDocs = needTopDocs? TopDocs.merge(0, len, topDocs): null; + } + int totalHits = needTopDocs? (int)mergedTopDocs.totalHits.value: -1; + maxScore = totalHits > 0 ? maxScore : 0.0f; + return new CollectorManagerResult(mergedTopDocs, docSet, maxScore, totalHits); + } + + }; + + CollectorManagerResult ret; + try { + ret = super.search(query, manager); + } catch (Exception ex) { + if (ex instanceof RuntimeException && + ex.getCause() != null & ex.getCause() instanceof ExecutionException + && ex.getCause().getCause() != null && ex.getCause().getCause() instanceof RuntimeException) { + throw (RuntimeException)ex.getCause().getCause(); + } else { + throw ex; + } + } + return ret; + } + + class CollectorManagerResult { Review comment: Make all fields final if you can ---------------------------------------------------------------- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. For queries about this service, please contact Infrastructure at: us...@infra.apache.org With regards, Apache Git Services --------------------------------------------------------------------- To unsubscribe, e-mail: issues-unsubscr...@lucene.apache.org For additional commands, e-mail: issues-h...@lucene.apache.org