簡體   English   中英

Java-拆分字符串,為字母數字

[英]Java- Split String which is alphanumeric

輸入示例:

RC23
CC23QQ21HD32
BPOASDf91A5HH123

輸出示例:

[RC,23]
[CC,23,QQ,21,HD,32]
[BPOASDf,91,A,5,HH,123]

字母和數字部分的長度不固定。

我知道如何將split()與//.' ' ' '([az])正則表達式結合使用//.' ' ' '([az]) //.' ' ' '([az])但是盡管我檢查了split() Java API,但找不到任何可以幫助我解決此問題的東西。

有沒有辦法使用split()做到這一點? 或者我需要使用另一種方法來拆分這些字符串。

任何幫助,將不勝感激。

試試這個正則表達式: "((?<=[a-zA-Z])(?=[0-9]))|((?<=[0-9])(?=[a-zA-Z]))"

這是一個正在運行的示例: http : //ideone.com/c02rmM

{
    ...
    String someString = "CC23QQ21HD32";
    String regex = "((?<=[a-zA-Z])(?=[0-9]))|((?<=[0-9])(?=[a-zA-Z]))";
    System.out.println(Arrays.asList(someString.split(regex)));
    //outputs [CC, 23, QQ, 21, HD, 32]
    ...
}

正則表達式使用前瞻 (?=ValueToMatch)和后 (?<=ValueToMatch)

它的前半部分(在|之前)問:“上一個字符是字母(?<=[a-zA-Z])嗎?下一個字符是數字(?=[0-9])嗎?” 如果兩者都為真,則將字符串與正則表達式匹配。

該正則表達式的后半部分正相反。 它詢問:“前一個字符是數字(?<=[0-9])嗎?下一個字符是字母嗎? (?=[a-zA-Z]) ”,並且如果兩個都為真正。

通常,split()會刪除正則表達式匹配的字符。 即使對於此正則表達式也是如此。 但是,由於正則表達式與0寬前瞻匹配,因此不會刪除您要查找的實際字符。

請查看Adam Paynter的答案,以獲取有關先行后退的更多信息如何在不使用Java刪除分隔符的情況下使用一些分隔符拆分字符串?

您可以匹配1個或多個連續的字母字符或1個或多個連續的數字字符。 序列中斷后,停止匹配,然后存儲序列,然后重新開始。 非單詞字符將被完全忽略。

編輯:我在下面創建了一個簡單的性能測試,以顯示使用String.split()Pattern.matcher()之間的速度。 拆分版本比matcher + loop版本快2.5倍。

private static String[] splitAlphaNumeric(String str) {
    return str.split("(?i)((?<=[A-Z])(?=\\d))|((?<=\\d)(?=[A-Z]))");
}

import java.util.*;
import java.util.regex.*;

public class SplitAlphaNumeric {
    private static final Pattern ALPH_NUM_PAT = Pattern.compile("[0-9]+|[A-Z]+");

    private static List<String> input = Arrays.asList(
        "RC23",
        "CC23QQ21HD32",
        "BPOASDf91A5HH123"
    );

    public static void main(String[] args) {
        System.out.printf("Execution time: %dns%n", testMatch());
        System.out.printf("Execution time: %dns%n", testSplit());
    }

    public static long testMatch() {
        System.out.println("Begin Test 1...");
        long start = System.nanoTime();
        for (String str : input) {
            System.out.printf("%-16s -> %s%n", str, parse(str));
        }
        long end = System.nanoTime();
        return end - start;
    }

    public static long testSplit() {
        System.out.println("\nBegin Test 2...");
        long start = System.nanoTime();
        for (String str : input) {
            System.out.printf("%-16s -> %s%n", str, parse2(str));
        }
        long end = System.nanoTime();
        return end - start;
    }

    private static List<String> parse(String str) {
        List<String> parts = new LinkedList<String>();
        Matcher matcher = ALPH_NUM_PAT.matcher(str);
        while (matcher.find()) {
            parts.add(matcher.group());
        }
        return parts;
    }

    private static List<String> parse2(String str) {
        return Arrays.asList(str.split("(?i)((?<=[A-Z])(?=\\d))|((?<=\\d)(?=[A-Z]))"));
    }
}

產量

Begin Test 1...
RC23             -> [RC, 23]
CC23QQ21HD32     -> [CC, 23, QQ, 21, HD, 32]
BPOASDf91A5HH123 -> [BPOASD, 91, A, 5, HH, 123]
Execution time: 4879125ns

Begin Test 2...
RC23             -> [RC, 23]
CC23QQ21HD32     -> [CC, 23, QQ, 21, HD, 32]
BPOASDf91A5HH123 -> [BPOASDf, 91, A, 5, HH, 123]
Execution time: 1953349ns

您可以使用前瞻,例如“ ((?<=%1[0-9]+)|(?=%1[0-9]+))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM