public Pair<Integer, Boolean> find(final boolean canMismatch) {
      if (myBeforeSide != null) {
        if (myBeforeSide) {
          // check only one side
          return new Pair<>(checkSide(myBeforeAfter.getBefore(), canMismatch), true);
        } else {
          // check only one side
          return new Pair<>(checkSide(myBeforeAfter.getAfter(), canMismatch), false);
        }
      } else {
        final int beforeCheckResult = checkSide(myBeforeAfter.getBefore(), canMismatch);
        final int afterCheckResult = checkSide(myBeforeAfter.getAfter(), canMismatch);

        final Pair<Integer, Boolean> beforePair = new Pair<>(beforeCheckResult, true);
        final Pair<Integer, Boolean> afterPair = new Pair<>(afterCheckResult, false);
        if (! canMismatch) {
          if (beforeCheckResult == 0) {
            return beforePair;
          }
          if (afterCheckResult == 0) {
            return afterPair;
          }
          return beforePair;
        }

        // take longer coinciding
        final int beforeCommon = myBeforeAfter.getBefore().size() - beforeCheckResult;
        final int afterCommon = myBeforeAfter.getAfter().size() - afterCheckResult;
        if (beforeCommon > 0 && afterCommon > 0) {
          // ignore insertion and deletion cases -> too few context -> if we have alternative
          if (beforeCommon == 1 && myBeforeAfter.getBefore().size() == 1 && afterCommon > 1) {
            return afterPair;
          }
          // ignore insertion and deletion cases -> too few context -> if we have alternative
          if (afterCommon == 1 && myBeforeAfter.getAfter().size() == 1 && beforeCommon > 1) {
            return beforePair;
          }
          if (beforeCommon >= afterCommon) {
            return beforePair;
          }
          return afterPair;
        }
        if (afterCommon > 0) {
          return afterPair;
        }
        return beforePair;
      }
    }
public Pair<Integer, Boolean> find(final boolean canMismatch)