在 Scala 中使用正则表达式

Suraj P 2023年1月30日 2022年6月15日
  1. Scala 中的 Regex
  2. 在 Scala 中查找文本中的匹配项
  3. 使用 Regex 替换 Scala 中的文本
  4. 使用 Regex 在 Scala 中提取值
  5. 结论
在 Scala 中使用正则表达式

正则表达式定义了用于匹配输入数据的通用模式。这些对于模式匹配和文本处理或解析非常有用。

在本文中,我们将学习如何在 Scala 中使用 Regex(正则表达式)。

Scala 中的 Regex

Regex 是 Scala 中的一个类,它是从 scala.util.matching.Regex 导入的,基于 Java 包 java.util.regex,广泛用于模式匹配和文本解析。Regex 对象可以通过两种方式创建。

第一种方法是显式创建 Regex 类对象。

val x = new Regex("you")

第二种方法是使用 r 方法。

val x = "You".r

让我们看一下使用 Regex 的正则表达式的不同用例。

在 Scala 中查找文本中的匹配项

在文本中查找匹配项是 Regex 最常见的用例之一。

示例代码:

import scala.util.matching.Regex
object myClass
{
    def main(args: Array[String])
    {
        val x = new Regex("Tony")
        val text = "Iron man is also known as Tony Stark. Tony is an Avenger"

        println(x findFirstIn text)
    }
}

输出:

Some(Tony)

运行代码

在上面的代码中,我们使用了 findFirstIn 方法来查找正则表达式的第一个匹配项,该方法返回一个 Option[String] 对象。

示例代码:

import scala.util.matching.Regex
object myClass
{
    def main(args: Array[String])
    {
        val reg = new Regex("([0-9]{2})\\-([0-9]{3})")
        val text = "He lives in Warsaw 01-011 and she lives in Cracow 30-059"

        println((reg findAllIn text).mkString(","))
    }
}

输出:

01-011,30-059

运行代码

在上面的示例中,我们使用 findAllIn 方法查找所有匹配项并返回 MatchIterator。然后我们使用 mkString 方法将输出转换为由 ,(逗号)分隔的字符串。

我们还有 findFirstMatchIn 方法。它的工作方式类似于 findFirstIn 方法,但返回 Option[Match]

示例代码:

import scala.util.matching.Regex
object myClass
{
    def main(args: Array[String])
    {
        val reg = new Regex("([0-9]{2})\\-([0-9]{3})")
        val text = "He lives in Warsaw 01-011 and she lives in Cracow 30-059"

        val result = reg.findFirstMatchIn(text)
        println(Some("011"), for (x <- result) yield x.group(2))
    }
}

输出:

(Some(011),Some(011))

运行代码

使用 Regex 替换 Scala 中的文本

这是替换文本的 Regex 的另一个用例。有时在文本解析期间,我们可能已经用其他东西替换了其中的一部分。

示例代码:

import scala.util.matching.Regex
object myClass
{
    // Main method
    def main(args: Array[String])
    {
        val reg = new Regex("([0-9]{2})\\-([0-9]{3})")
        val text = "He lives in Warsaw 01-011 and she lives in Cracow 30-059"

        println(reg replaceFirstIn(text, "1234"))
    }
}

输出:

He lives in Warsaw 1234 and she lives in Cracow 30-059

运行代码

在上面的代码中,我们使用了 replaceFirstIn 方法将文本中找到的第一个匹配项替换为字符串 "1234"

示例代码:

import scala.util.matching.Regex
object myClass
{
    // Main method
    def main(args: Array[String])
    {
        val reg = new Regex("([0-9]{2})\\-([0-9]{3})")
        val text = "He lives in Warsaw 01-011 and she lives in Cracow 30-059"

        println(reg replaceAllIn(text, "1234"))
   }
}

输出:

He lives in Warsaw 1234 and she lives in Cracow 1234

运行代码

在上面的代码中,我们使用了 replaceAllIn 方法,它将在文本中找到的所有匹配项替换为 "1234"

使用 Regex 在 Scala 中提取值

当我们使用正则表达式找到匹配项时,我们可以使用 Regex 通过模式匹配来提取值。

示例代码:

import scala.util.matching.Regex
object myClass {

    def main(args: Array[String]) {
        val timestamp = "([0-9]{2}):([0-9]{2}):([0-9]{2}).([0-9]{3})".r
        val time = "12:20:01.411" match {
            case timestamp(hour, minutes, _, _) => println(s"It is $minutes minutes after $hour")
        }
    }
}

输出:

It is 20 minutes after 12

运行代码

在 Scala 中,默认情况下,Regex 的行为就像模式是 anchored。例如,模式被放在^$ 字符的中间,如^pattern$,但我们可以使用 UnanchoredRegex 类中的 unanchored 方法删除这些字符。

有了这个帮助,我们可以在字符串中添加额外的文本,并且仍然可以找到我们需要的内容。

示例代码:

import scala.util.matching.Regex
object myClass
{
    def main(args: Array[String]) {
        val timestamp = "([0-9]{2}):([0-9]{2}):([0-9]{2}).([0-9]{3})".r
        val temp = timestamp.unanchored
        val time = "It is 12:20:01.411 in New York" match {
            case temp(hour, minutes, _, _) => println(s"It is $minutes minutes after $hour")
        }
    }
}

输出:

It is 20 minutes after 12

运行代码

Java 从 Perl 编程语言继承了它的大部分正则表达式和它的 Regex 特性,而 Scala 从 Java 继承了它的正则表达式语法。

让我们看一下从 Java 中提取的一些 Scala 常用的正则表达式。

子表达式 匹配
^ 它匹配行的开头。
$ 它与结尾的开头相匹配。
[...] 它用于匹配括号中存在的任何单个字符。
[^...] 它用于匹配括号中不存在的任何单个字符
\\w 它用于匹配单词字符。
\\d 它用于匹配数字。

结论

在本文中,我们了解了 Scala 标准库中的 Regex 类。我们还看到了它如何提供不同的 API,帮助我们处理正则表达式的不同用例。

Author: Suraj P
Suraj P avatar Suraj P avatar

A technophile and a Big Data developer by passion. Loves developing advance C++ and Java applications in free time works as SME at Chegg where I help students with there doubts and assignments in the field of Computer Science.

LinkedIn GitHub