具有附加格式的 Scala 正则表达式 find/replace

Scala regex find/replace with additional formatting

我正在尝试替换包含应该是日期但可能采用不允许的格式的字符串部分。具体来说,所有日期都采用 "mm/dd/YYYY" 格式,并且它们需要采用 "YYYY-mm-dd" 格式。需要注意的是,原始日期可能 不完全 是 mm/dd/YYYY 格式;有些像“5/6/2015”。例如,如果

val x = "where date >= '05/06/2017'"

然后

x.replaceAll("'([0-9]{1,2})/([0-9]{1,2})/([0-9]{4})'", "'--'")

执行所需的替换(returns "2017-05-06"),但对于

val y = "where date >= '5/6/2017'"

这不是 return 所需的替换(returns“2017-5-6”——对我来说,这是一个无效的表示)。使用 Joda Time 包装器 nscala-time,我尝试捕获日期然后重新格式化它们:

import com.github.nscala_time.time.Imports._
import org.joda.time.DateTime

val f = DateTimeFormat.forPattern("yyyy-MM-dd")
y.replaceAll("'([0-9]{1,2}/[0-9]{1,2}/[0-9]{4})'",
   "'"+f.print(DateTimeFormat.forPattern("MM/dd/yyyy").parseDateTime(""))+"'")

但这失败了 java.lang.IllegalArgumentException: Invalid format: ""。我也尝试过使用 f 插值器并用 0 填充,但它似乎也不喜欢那样。

您是否无法对 replaceAll 中捕获的组( 等)进行额外处理?如果没有,我还能如何达到预期的结果?

Regex.replaceAllIn 已过载,可以采用 Match => String。

</code> 之类的反向引用只能在字符串替换模式中使用。在您的代码中,<code>"" 不再是反向引用。

您可以使用 "callback" 和 replaceAllIn 来实际获取匹配对象并访问其组以进一步操作它们:

val pattern = "'([0-9]{1,2}/[0-9]{1,2}/[0-9]{4})'".r
y = pattern replaceAllIn (y, m => "'"+f.print(DateTimeFormat.forPattern("MM/dd/yyyy").parseDateTime(m.group(1)))+"'")