public static @NotNull List<String> parse(@NotNull String parameterString,
                                            boolean keepQuotes,
                                            boolean supportSingleQuotes,
                                            boolean keepEmptyParameters) {
    if (!keepEmptyParameters) {
      parameterString = parameterString.trim();
    }

    final List<String> params = new ArrayList<>();
    if (parameterString.isEmpty()) {
      return params;
    }
    final StringBuilder token = new StringBuilder(128);
    boolean inQuotes = false;
    boolean escapedQuote = false;
    IntSet possibleQuoteChars = new IntOpenHashSet();
    possibleQuoteChars.add('"');
    if (supportSingleQuotes) {
      possibleQuoteChars.add('\'');
    }
    char currentQuote = 0;
    boolean nonEmpty = false;

    for (int i = 0; i < parameterString.length(); i++) {
      final char ch = parameterString.charAt(i);
      if ((inQuotes ? currentQuote == ch : possibleQuoteChars.contains(ch))) {
        if (!escapedQuote) {
          inQuotes = !inQuotes;
          currentQuote = ch;
          nonEmpty = true;
          if (!keepQuotes) {
            continue;
          }
        }
        escapedQuote = false;
      }
      else if (Character.isWhitespace(ch)) {
        if (!inQuotes) {
          if (keepEmptyParameters || token.length() > 0 || nonEmpty) {
            params.add(token.toString());
            token.setLength(0);
            nonEmpty = false;
          }
          continue;
        }
      }
      else if (ch == '\\' && i < parameterString.length() - 1) {
        final char nextchar = parameterString.charAt(i + 1);
        if (inQuotes ? currentQuote == nextchar : possibleQuoteChars.contains(nextchar)) {
          escapedQuote = true;
          if (!keepQuotes) {
            continue;
          }
        }
      }

      token.append(ch);
    }

    if (keepEmptyParameters || token.length() > 0 || nonEmpty) {
      params.add(token.toString());
    }

    return params;
  }
public static @NotNull List<String> parse(@NotNull String parameterString,
                                            boolean keepQuotes,
                                            boolean supportSingleQuotes,
                                            boolean keepEmptyParameters)