/**
   * This need to be thread safe
   *
   * @param seq
   * @param outStream
   * @throws IOException
   */
  private void processReads(Sequence seq, PrintStream outStream) throws IOException {
    NuclKmerGenerator kmerGenerator;
    Kmer kmer;

    boolean found = false;
    kmerGenerator = new NuclKmerGenerator(seq.getSeqString(), kmerSize);
    while (kmerGenerator.hasNext()) {

      kmer = kmerGenerator.next();
      for (int i = 0; i < kmerMaps.length; i++) { // for forward and reverse direction
        KmerAbund kmerAbund = kmerMaps[i].get(kmer);
        if (kmerAbund != null) {
          // increment the count
          kmerAbund.count.addAndGet(1);
          found = true;
        }
      }
    }
    if (found) {
      totalReads.incrementAndGet();
    }
    if (outStream != null && found) {
      writeSeq(seq, outStream);
    }
  }
  /**
   * find the kmers in the contigs
   *
   * @param reader
   * @throws IOException
   */
  private void processContigFile(SequenceReader reader) throws IOException {
    Sequence seq;
    NuclKmerGenerator kmerGenerator;
    Kmer kmer;
    int contigIdx = 0;
    while ((seq = reader.readNextSequence()) != null) {
      if (seq.getSeqString().length() < kmerSize) {
        continue;
      }
      // use int to represent seqname in case contig names are too long
      contigMap.put(
          contigIdx, new Contig(seq.getSeqName(), seq.getSeqString().length() - kmerSize + 1));
      // forward direction
      kmerGenerator = new NuclKmerGenerator(seq.getSeqString(), kmerSize);
      while (kmerGenerator.hasNext()) {
        kmer = kmerGenerator.next();
        KmerAbund kmerAbund = kmerMaps[0].get(kmer);

        if (kmerAbund == null) {
          kmerAbund = new KmerAbund();
          kmerMaps[0].put(kmer, kmerAbund);
        }
        kmerAbund.contigList.add(new ContigCoverage(contigIdx, kmerGenerator.getPosition() - 1));
      }

      // reverse direction
      kmerGenerator =
          new NuclKmerGenerator(IUBUtilities.reverseComplement(seq.getSeqString()), kmerSize);
      while (kmerGenerator.hasNext()) {
        kmer = kmerGenerator.next();
        KmerAbund kmerAbund = kmerMaps[1].get(kmer);

        if (kmerAbund == null) {
          kmerAbund = new KmerAbund();
          kmerMaps[1].put(kmer, kmerAbund);
        }
        kmerAbund.contigList.add(
            new ContigCoverage(
                contigIdx,
                seq.getSeqString().length() - kmerGenerator.getPosition() - kmerSize + 1));
      }
      contigIdx++;
    }
    reader.close();
  }