按新行拆分Java字符串

dr.*_*an 372 java regex split newline

我正在尝试JTextArea使用正则表达式拆分文本以拆分字符串\n然而,这不起作用,我也试过\r\n|\r|n和许多其他正则表达式的组合.码:

public void insertUpdate(DocumentEvent e) {
    String split[], docStr = null;
    Document textAreaDoc = (Document)e.getDocument();

    try {
        docStr = textAreaDoc.getText(textAreaDoc.getStartPosition().getOffset(), textAreaDoc.getEndPosition().getOffset());
    } catch (BadLocationException e1) {
        // TODO Auto-generated catch block
        e1.printStackTrace();
    }

    split = docStr.split("\\n");
}
Run Code Online (Sandbox Code Playgroud)

cle*_*tus 694

这应该涵盖你:

String lines[] = string.split("\\r?\\n");
Run Code Online (Sandbox Code Playgroud)

您只需要担心两个新行(UNIX和Windows).

  • JTextArea文档应该只使用'\n'; 它的视图完全忽略'\ r'.但是如果你要寻找多种分隔符,你也可以寻找所有这三种分隔符:"\ r?\n |\r". (42认同)
  • Mac 9使用\ r \n.OSX 10使用\n (10认同)
  • @antak是的,`split`默认情况下会删除尾随的空字符串,如果它们是split的结果.要关闭此机制,您需要使用带有负限制的`split(regex,limit)`的重载版本,如`text.split("\\ r?\\n", - 1)`.更多信息:[Java String split拆除空值](http://stackoverflow.com/questions/14602062/java-string-split-removed-empty-values) (4认同)

Gum*_*mbo 126

如果你不想要空行:

String.split("[\\r\\n]+")
Run Code Online (Sandbox Code Playgroud)

  • @giulio是的,我知道(参见[了解Java中的正则表达式:split("\ t")vs split("\\ t") - 它们何时工作,何时应该使用](http:// stackoverflow .COM /问题/ 3762347 /了解正则表达式,在Java的分裂-T-VS-分裂叔当-DO-他们-都-WOR/3762377#3762377)). (7认同)
  • 不需要双反斜杠,请参阅"反斜杠,转义和引用"部分http://docs.oracle.com/javase/1.4.2/docs/api/java/util/regex/Pattern.html (4认同)
  • @tresf 您不能在方括号中使用量词。 (2认同)

Psh*_*emo 113

String#split?(String regex)方法是使用正则表达式(正则表达式).由于Java 8正则表达式支持\R代表(来自Pattern类的文档):

Linebreak matcher
\R任何Unicode换行序列,相当于 \u000D\u000A|[\u000A\u000B\u000C\u000D\u0085\u2028\u2029]

所以我们可以用它来匹配:

如您所见,\r\n它位于正则表达式的开头,它确保正则表达式首先尝试匹配该,并且只有当该匹配失败时,它才会尝试匹配单个字符行分隔符.


所以如果你想拆分线上分隔符使用split("\\R").

如果你不想从结果数组中删除空字符串,请""使用split(regex, limit)limit参数之类的split("\\R", -1).

如果要将一个或多个连续的空行视为单个分隔符使用split("\\R+").

  • 是的,这是最好的答案。不幸的是,这个问题提早了六年才得到这个答案。 (7认同)

She*_*ari 45

String.split(System.getProperty("line.separator"));
Run Code Online (Sandbox Code Playgroud)

这应该是系统独立的

  • 这是一个有趣的想法,但你应该注意文本实际上使用系统的行分隔符.我在unix(例如XML)下使用"Windows"分隔符和很多使用unix分隔符的Windows下的很多文本文件. (39认同)
  • 这是一个非常有问题的方法!该文件可能不是源自运行代码的系统.我强烈反对这些实际依赖于特定系统即运行时系统的"系统独立"设计. (16认同)
  • 在Windows操作系统中创建并转移到Unix操作系统的文件仍将包含\ r \n分隔符.我认为最好安全地玩两个分离器. (6认同)
  • @Shervin这绝不是最好的方法.事实上这是非常糟糕的做法.考虑一些其他程序员调用System.setProperty("line.separator","你没有意义"); 你的代码坏了.它甚至可能被你不了解的依赖性类似地调用. (3认同)

Mar*_*tin 12

您不必在字符组中双重转义字符.

对于所有非空行使用:

String.split("[\r\n]+")
Run Code Online (Sandbox Code Playgroud)

  • 代码中的双反斜杠"'\\'`变为`'\''字符,然后传递给RegEx引擎,所以代码中的``[\\ r \\n]"`变成`[\ r \n ]`在内存中,RegEx将处理它.我不知道Java如何处理RegEx,但将"纯"ASCII字符串模式传递给RegEx引擎并让它处理而不是传递二进制字符是一个好习惯.`"[\ r \n]"`在内存中变为(十六进制)`0D0A`,一个RegEx引擎可能接受它而另一个会阻塞.所以最重要的是,即使Java的RegEx风格不需要它们,也要保持双斜杠以保持兼容性 (2认同)

Ant*_*iuc 10

lines引入了一个新方法,该方法返回StringStream<String>

返回从由行终止符分区的此字符串中提取的子字符串流.

识别的行终止符是换行符"\n"(U + 000A),回车符"\ r"(U + 000D)和回车后紧跟换行符"\ r \n"(U + 000D U + 000A) ).

这里有一些例子:

jshell> "lorem \n ipusm \n sit".lines().forEach(System.out::println)
lorem
 ipusm
 sit

jshell> "lorem \n ipusm \r  sit".lines().forEach(System.out::println)
lorem
 ipusm
  sit

jshell> "lorem \n ipusm \r\n  sit".lines().forEach(System.out::println)
lorem
 ipusm
  sit
Run Code Online (Sandbox Code Playgroud)

串#线()


Mic*_*ael 7

也许这会奏效:

从split方法的参数中删除双反斜杠:

split = docStr.split("\n");
Run Code Online (Sandbox Code Playgroud)

  • 并不是的.当您以Java String文字的形式编写正则表达式时,可以使用"\n"将正则表达式编译器传递给换行符号,或者使用"\\n"将换行符传递给换行符.除了\ v之外的所有其他空格转义也是如此,这在Java文字中是不受支持的. (8认同)
  • @Yuval.抱歉这是不正确的,你根本不需要它"反斜杠,转义和引用"http://docs.oracle.com/javase/1.4.2/docs/api/java/util/regex/Pattern.html (3认同)

Til*_*fer 7

实际上,这里给出的所有答案都不符合Java对新行的定义,例如BufferedReader#readline。Java正在接受\n\r并将其\r\n作为新行。一些答案匹配多个空行或格式错误的文件。例如。<sometext>\n\r\n<someothertext>使用时[\r\n]+将导致两行。

String lines[] = string.split("(\r\n|\r|\n)", -1);
Run Code Online (Sandbox Code Playgroud)

相反,以上答案具有以下属性:

  • 它符合Java对新行的定义,例如BufferedReader正在使用它
  • 它与多个新行不匹配
  • 它不会删除尾随的空行


Ous*_* D. 6

JDK11所述String类有一个lines()方法:

返回从此字符串中提取的行流,以行终止符分隔。

此外,文档继续说:

行终止符是以下之一:换行符“ \ n”(U + 000A),回车符“ \ r”(U + 000D)或回车符后紧跟换行符“ \ r \ n“(U + 000D U + 000A)。行要么是零个或多个字符的序列,后跟一个行终止符,要么是一个或多个字符的序列,后跟字符串的结尾。一行不包括行终止符。

有了这个,就可以做到:

Stream<String> stream = str.lines();
Run Code Online (Sandbox Code Playgroud)

然后,如果您想要一个数组:

String[] array = str.lines().toArray(String[]::new);
Run Code Online (Sandbox Code Playgroud)

给定此方法后,Stream将为您提供很多选择,因为它使您能够编写可能并行操作的简洁声明式表达式。


sev*_*rce 5

为了防止空行被压扁,请使用:

String lines[] = String.split("\\r?\\n", -1);
Run Code Online (Sandbox Code Playgroud)


Dan*_*nga 5

如果由于某种原因而不想使用String.split(例如,由于使用正则表达式),并且想要在Java 8或更高版本上使用函数式编程,请执行以下操作:

List<String> lines = new BufferedReader(new StringReader(string))
        .lines()
        .collect(Collectors.toList());
Run Code Online (Sandbox Code Playgroud)

  • 或`String [] lines = new BufferedReader(...)。lines()。toArray(String [] :: new);`用于数组而不是列表。这个解决方案的优点是,`BufferedReader`知道各种类似的终止符,因此它可以处理各种格式的文本。(在此发布的大多数基于正则表达式的解决方案在这方面都不够。) (2认同)
  • 自从Java 11和引入String.lines()方法以来,该解决方案就已经过时了。 (2认同)

小智 5

上面的答案对我在 Android 上没有帮助,感谢Pshemo响应在 Android 上对我有用。我将在这里留下Pshemo 的一些回答:

split("\\\\n")
Run Code Online (Sandbox Code Playgroud)