有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java正则表达式匹配从A到Z的单个字母

我希望正则表达式匹配字符串中的单个字母(按顺序从a到Z):

它应该找到字母“A”,如果没有字母“A”,它应该找到字母“B”,然后是字母“C”,依此类推

示例->

  • BCDAE

  • CBDE->;因为没有“A”,所以它与B

  • YXZ

  • BAAC->;因为有两个A,它找到最左边的 角色优先


额外信息:

我举个例子,因为有些用户似乎不喜欢没有代码的问题

Given a lower case string remove k characters from that string. First remove all letter 'a', followed by letter 'b', then 'c', etc..

。这就是我的解决方案:

public static String remove(String s, int k) {
  for (int c : s.chars().sorted().limit(k).toArray())
    s = s.replaceFirst(Character.toString((char) c), "");
  return s;
}

但是我想用一个正则表达式来试试这个,比如:

public static String remove(String s, int k) {
  while (k-- > 0)
    s = s.replaceFirst(MY_MAGIC_REGEX_STR, "");
  return s;
}

共 (2) 个答案

  1. # 1 楼答案

    以下正则表达式可以根据需要工作:

    (?i)A|B(?!.*[A-A])|C(?!.*[A-B])|D(?!.*[A-C])|E(?!.*[A-D])|F(?!.*[A-E])|G(?!.*[A-F])|H(?!.*[A-G])|I(?!.*[A-H])|J(?!.*[A-I])|K(?!.*[A-J])|L(?!.*[A-K])|M(?!.*[A-L])|N(?!.*[A-M])|O(?!.*[A-N])|P(?!.*[A-O])|Q(?!.*[A-P])|R(?!.*[A-Q])|S(?!.*[A-R])|T(?!.*[A-S])|U(?!.*[A-T])|V(?!.*[A-U])|W(?!.*[A-V])|X(?!.*[A-W])|Y(?!.*[A-X])|Z(?!.*[A-Y])
    

    正则表达式由26个术语组成(每个字母一个术语),它们通过交替运算符(|)连接在一起。A(?B)是负前瞻运算符,如果A后面不跟B,则与A相匹配。(?i)只是触发大小写不敏感

    总的来说,正则表达式首先从左到右找到所有A,而不是从左到右找到所有B,依此类推

    由于正则表达式的长度,以编程方式生成它更为方便:

    // Generate regEx
    String regEx = "(?i)" + "A" + "|";  
    for (char i = 'B'; i <= 'Z'; i++ ) {
        regEx += i + "(?!.*[A-" + (char)(i-1) + "])" + "|";
    }
    regEx = regEx.substring(0, regEx.length() - 1);
    System.out.println(regEx);
    

    对于以下示例:

    String example = "AAAZZZHHAAAZZHHHAAZZZHH"; 
    
    // Output
    while(example.length() != 0) {
        System.out.println(example);
        example = example.replaceFirst(regEx, "");
    }
    

    输出为:

    AAAZZZHHAAAZZHHHAAZZZHH
    AAZZZHHAAAZZHHHAAZZZHH
    AZZZHHAAAZZHHHAAZZZHH
    ZZZHHAAAZZHHHAAZZZHH
    ZZZHHAAZZHHHAAZZZHH
    ZZZHHAZZHHHAAZZZHH
    ZZZHHZZHHHAAZZZHH
    ZZZHHZZHHHAZZZHH
    ZZZHHZZHHHZZZHH
    ZZZHZZHHHZZZHH
    ZZZZZHHHZZZHH
    ZZZZZHHZZZHH
    ZZZZZHZZZHH
    ZZZZZZZZHH
    ZZZZZZZZH
    ZZZZZZZZ
    ZZZZZZZ
    ZZZZZZ
    ZZZZZ
    ZZZZ
    ZZZ
    ZZ
    Z
    
  2. # 2 楼答案

    正则表达式可能不是解决这个问题的最佳工具。我认为最简单的方法是将输入字符串转换成一个字符数组,然后沿着该数组遍历,跟踪最小(最小)字符是什么:

    public char findLowestChar(String input) {
        char[] array = input.toCharArray();
        char chr = 'Z';     // works so long as input is non-empty
        for (int i=0; i < array.length; ++i) {
            if (array[i] < chr) {
                chr = array[i];
            }
        }
        return chr;
    }
    

    这里我假设输入字符串中至少有一个字母A-Z。如果没有,并且您还希望在方法中实现这一点,那么您还应该处理空输入案例

    编辑:

    你刚刚实质性地改变了你的问题。但事实证明,上述代码仍然可以作为更新答案的一部分。现在,您可以迭代k次,并在每一步运行上述代码以找到最低的字母。然后,执行String#replaceAll删除该字母的所有匹配项

    String input = "BCDAE";
    // remove k=4 characters, starting with (maybe) A, from the input string
    for (int k=0; k < 4 && input.length() > 0; ++k) {
        char lowest = findLowestChar(input);
        input = input.replaceAll(String.valueOf(lowest), "");
    }