Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python:在特定条件下查找并替换为正则表达式_Python_Regex - Fatal编程技术网

Python:在特定条件下查找并替换为正则表达式

Python:在特定条件下查找并替换为正则表达式,python,regex,Python,Regex,基本上我想写一个脚本来清理URL,用“(点)”字符串替换点。 例如,如果在我运行脚本之后,我希望它是。 这很容易实现。当我的文本文件只包含URL或其他字符串时,请替换,但在我的情况下,我的文本文件中也有IP地址,我不希望IP地址中的点更改为“(点)” 我试图使用正则表达式来实现这一点,但我的输出是 " 192.60.10.10 33.44.55.66“ 这是我的密码 from __future__ import print_function import sys import re na

基本上我想写一个脚本来清理URL,用“(点)”字符串替换点。 例如,如果在我运行脚本之后,我希望它是。 这很容易实现。当我的文本文件只包含URL或其他字符串时,请替换,但在我的情况下,我的文本文件中也有IP地址,我不希望IP地址中的点更改为“(点)”

我试图使用正则表达式来实现这一点,但我的输出是 " 192.60.10.10 33.44.55.66“

这是我的密码

from __future__ import print_function


import sys
import re

nargs = len(sys.argv)
if nargs < 2:

    sys.exit('You did not specify a file')
else:
    inputFile = sys.argv[1]
    fp = open(inputFile)
    content = fp.read()

replace = '(dot)'
regex = '[a-z](\.)[a-z]'
print(re.sub(regex, replace, content, re.M| re.I| re.DOTALL))
from\uuuuu future\uuuuu导入打印功能
导入系统
进口稀土
nargs=len(sys.argv)
如果nargs<2:
sys.exit('您没有指定文件')
其他:
inputFile=sys.argv[1]
fp=打开(输入文件)
content=fp.read()
替换='(点)'
正则表达式='[a-z](\)[a-z]'
打印(re.sub(正则表达式、替换、内容、re.M | re.I | re.DOTALL))

我想我需要有一个条件来检查模式是否为number.number-不要替换。

您可以使用lookahead和lookahead断言:

import  re

s = "http://www.google.com 127.0.0.1"

print(re.sub("(?<=[a-z])\.(?=[a-z])", "(dot)", s))
http://www(dot)google(dot)com 127.0.0.1
如果文件太大,并且内存有问题,您也可以逐行执行,或者将所有行存储在列表中,或者在执行时使用每一行:

import re
with open("test.txt") as f:
    r = re.compile("(?=.*[a-z])(?<=\w)\.(?=\w)", re.I)
    lines = [r.sub("(?=.*[a-z])(?<=\w)\.(?=\w)", "(dot)") for line in f]
重新导入
以open(“test.txt”)作为f:

r=re.compile((?=.[a-z])(?您必须在点之前和之后存储
[a-z]
内容,以将其再次放入替换的字符串中。我是如何解决它的:

from __future__ import print_function
import sys
import re

nargs = len(sys.argv)
if nargs < 2:
    sys.exit('You did not specify a file')
else:
    inputFile = sys.argv[1]
    fp = open(inputFile)
    content = fp.read()

replace = '\\1(dot)\\3'
regex = '(.*[a-z])(\.)([a-z].*)'
print(re.sub(regex, replace, content, re.M| re.I| re.DOTALL))
from\uuuuu future\uuuuu导入打印功能
导入系统
进口稀土
nargs=len(sys.argv)
如果nargs<2:
sys.exit('您没有指定文件')
其他:
inputFile=sys.argv[1]
fp=打开(输入文件)
content=fp.read()
替换='\\1(点)\\3'
正则表达式='(.[a-z])(\)([a-z].]
打印(re.sub(正则表达式、替换、内容、re.M | re.I | re.DOTALL))

根据您的代码判断,您希望替换模式中的第一组。但是,
re.sub
替换整个匹配模式,而不是一组。在您的情况下,这是句点前的单个字符、句点本身以及句点后的单个字符

即使sub按您所希望的那样工作,您的正则表达式也会缺少数字是URL一部分的边缘情况,例如
www.2048game.com
。 定义IP的外观要容易得多。它总是由四个数字组成,每个数字有一个、两个或三个数字,用点分隔。(无论如何,在IPv4的情况下。但是IPv6不使用句点,所以在这里不重要。)

假设文本文件中只有URL和IP,只需过滤掉所有IP,然后替换其余URL中的句点:

is_ip = re.compile('\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}')
urls = content.split(" ")
for i, url in enumerate(urls):
    if not is_ip.match(url):
        urls[i] = url.replace('.', '(dot)')
content = ' '.join(urls)

当然,如果您在
内容中有规则文本,这也将替换所有规则句点,而不仅仅是URL。在这种情况下,您将首先需要更复杂的URL检测。请参阅好。这几乎适用于所有情况。但是,域名中的数字是合法的。此外,这还取决于存储在较低CA中的域名e、 @StevenRumbalski,我只是基于OP自己的代码和他们只使用
[a-z]的事实
在他们的模式中,我把旗帜留给了OPFair。出于值得的考虑,我投票给了你的答案。但我仍然认为这是一个大问题,它无法处理
'io9.com'
。case的问题很小,也很容易解决。@StevenRumbalski,别担心,我正在为有数字的情况做一些工作volvedi对此进行了测试,它可以在1到2行文本中正常工作,但不起作用。我的意思是,它只会替换文本的开头,对于一个内部有192.60.10.10 33.44.55.66的文本文件,它只会替换
'www.google.com'
giving
'www.google(dot)的第一个URL失败此外,数字在域名中是合法的,因此在这些域名上也会失败(考虑io9.com)。问题是匹配项没有重叠。请参阅Padraic Cunningham的答案,了解如何使用前向和后向断言解决此问题。经过测试,它还替换了ip地址中的点抱歉,代码中有一个拼写错误。您当然应该调用
is_ip.match(url)
,而不是
is_ip.match(内容)
太好了,但它为什么要更改输出结构呢?我的意思是,当我打开包含已保存内容的文本文档时,所有内容都排在一长行中,而不是更改前的结构。@Vlad啊,我的另一个失误。
split()
不使用任何空格分隔参数,可以是空格字符或换行符。请改用
分隔(“”)
from __future__ import print_function
import sys
import re

nargs = len(sys.argv)
if nargs < 2:
    sys.exit('You did not specify a file')
else:
    inputFile = sys.argv[1]
    fp = open(inputFile)
    content = fp.read()

replace = '\\1(dot)\\3'
regex = '(.*[a-z])(\.)([a-z].*)'
print(re.sub(regex, replace, content, re.M| re.I| re.DOTALL))
is_ip = re.compile('\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}')
urls = content.split(" ")
for i, url in enumerate(urls):
    if not is_ip.match(url):
        urls[i] = url.replace('.', '(dot)')
content = ' '.join(urls)
import re

content = "I tried to do this using regex, but my output is http://www.googl.com 192.60.10.10 33.44.55.66\nhttp://ya.ru\n..."

reg = r'http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\(\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+'

all_urls = re.findall(reg, content, re.M| re.I| re.DOTALL)
repl_urls = [u.replace('.', '(dot)') for u in all_urls]

for u, r in zip(all_urls, repl_urls):
    content = content.replace(u, r)

print content