2

I'm trying to change a string that contains substrings such as

the</span></p>
<p><span class=font7>currency

to

the currency

At the line break is CRLF

The words before and after the code change. I only want to replace if the second word starts with a lower case letter. The only thing that changes in the code is the digit after 'font'

I tried:

p = re.compile('</span></p>\r\n<p><span class=font\d>([a-z])')
res = p.sub(' \1', data)

but this isn't working

How should I fix this?

foosion
  • 7,619
  • 25
  • 65
  • 102

3 Answers3

1

Use a lookahead assertion.

p = re.compile('</span></p>\r\n<p><span class=font\d>(?=[a-z])')
res = p.sub(' ', data)
Peter Graham
  • 11,323
  • 7
  • 40
  • 42
1

This :

result = re.sub("(?si)(.*?)</?[A-Z][A-Z0-9]*[^>]*>.*</?[A-Z][A-Z0-9]*[^>]*>(.*)", r"\1 \2", subject)

Applied to :

the</span></p>
<p><span class=font7>currency

Produces :

the currency

Although I would strongly suggest against using regex with xml/html/xhtml. THis generic regex will remove all elements and capture any text before / after to groups 1,2.

FailedDev
  • 26,680
  • 9
  • 53
  • 73
  • The reason the html seems reversed is that you're seeing the end of one paragraph and the beginning of another. That regex seems very complex – foosion Oct 16 '11 at 00:20
  • @foosion Well this regex will work regardless of any elements you throw in it. – FailedDev Oct 16 '11 at 00:26
1

I think you should use the flag re.DOTALL, which means it will "see" nonprintable characters, such as linebreaks, as if they were regular characters.

So, first line of your code would become :

p = re.compile('</span></p>..<p><span class=font\d>([a-z])', re.DOTALL)

(not the two unescaped dots instead of the linebreak).

Actually, there is also re.MULTILINE, everytime I have a problem like this one of those end up solving the problem.

Hope it helps.

heltonbiker
  • 26,657
  • 28
  • 137
  • 252