0

这是我的另一个问题的后续。我发现的解决方案对我投入的每一个测试用例都非常有效,直到出现一个第一次让我无法理解的案例。

我的目标是使用正则表达式重新格式化格式不正确的标签属性(我知道,可能不是我发现的万无一失的方法,但请耐心等待)。

我的职能:

Public Function ConvertMarkupAttributeQuoteType(ByVal html As String) As String
    Dim findTags As String = "</?\w+((\s+\w+(\s*=\s*(?:"".*?""|'.*?'|[^'"">\s]+))?)+\s*|\s*)/?>"
    Return Regex.Replace(html, findTags, AddressOf EvaluateTag)
End Function

Private Function EvaluateTag(ByVal match As Match) As String
    Dim attributes As String = "\s*=\s*(?:(['""])(?<g1>(?:(?!\1).)*)\1|(?<g1>\S+))"
    Return Regex.Replace(match.Value, attributes, "='$2'")
End Function

函数中的正则表达式EvaluateTag将正确地转换 HTML,如

<table border=2 cellpadding='2' cellspacing="1">

进入

<table border='2' cellpadding='2' cellspacing='1'>

你会注意到我强制属性值用单引号括起来——不用担心。它中断的情况是最后一个属性值周围没有任何东西。

<table width=100 border=0>

来自正则表达式替换为

<table width='100' border='0>'

最后一个单引号错误地位于标签之外。我之前承认我根本不擅长正则表达式;我只是没有花时间去理解它所能做的一切。所以,我请求一些帮助来调整EvaluateTag正则表达式,以便它可以处理最后的情况。

谢谢!

4

2 回答 2

1

第一个 RegEx 函数将传递 EvaluateTag整个匹配项,即整个 HTML 标记。

但是 EvaluateTag 并没有忽略最后的大于字符......

恐怕我还没有足够的咖啡因来处理整个表达式,但是这种调整可能会起作用(在字符列表中添加了一个大于):

 Private Function EvaluateTag(ByVal match As Match) As String
   Dim attributes As String = "\s*=\s*(?:(['"">])(?<g1>(?:(?!\1).)*)\1|(?<g1>\S+))"
   Return Regex.Replace(match.Value, attributes, "='$2'")
 End Function
于 2009-09-14T16:00:06.613 回答
1

richardtallent 对为什么正则表达式不起作用的解释为我指明了正确的方向。在玩了一会儿之后,以下 EvaluateTag 函数的替换似乎正在起作用。

有人能看出它有什么问题吗?我所做的更改是在管道之后的最后一组。也许它可以进一步简化?

 Private Function EvaluateTag(ByVal match As Match) As String
   Dim attributes As String = "\s*=\s*(?:(['""])(?<g1>(?:(?!\1).)*)\1|(?<g1>[^>\s]+))"
   Return Regex.Replace(match.Value, attributes, "='$2'")
 End Function

如果没有人回应,我可能会接受这个作为答案。再次感谢!

于 2009-09-15T01:27:15.840 回答