python实现的用于搜索文件并进行内容替换的类实例
本文实例讲述了python实现的用于搜索文件并进行内容替换的类。分享给大家供大家参考。具体实现方法如下:
#!/usr/bin/python-O
#coding:UTF-8
"""
-replacestringinfiles(recursive)
-displaythedifference.
v0.2
-search_stringcanbeare.compile()object->usere.subforreplacing
v0.1
-initialversion
Useablebyasmall"client"script,e.g.:
-------------------------------------------------------------------------------
#!/usr/bin/python-O
#coding:UTF-8
importsys,re
#sys.path.insert(0,"/path/to/git/repro/")#Pleasechangepath
fromreplace_in_filesimportSearchAndReplace
SearchAndReplace(
search_path="/to/the/files/",
#e.g.:simplestringreplace:
search_string='theoldstring',
replace_string='thenewstring',
#e.g.:Regularexpressionreplacing(usedre.sub)
#search_string=re.compile('{%url(.*?)%}'),
#replace_string="{%url'\g<1>'%}",
search_only=True,#Displayonlythedifference
#search_only=False,#writethenewcontent
file_filter=("*.py",),#fnmatch-Filter
)
-------------------------------------------------------------------------------
:copyleft:2009-2011byJensDiemer
"""
__author__="JensDiemer"
__license__="""GNUGeneralPublicLicensev3orabove-
http://www.opensource.org/licenses/gpl-license.php"""
__url__="http://www.jensdiemer.de"
__version__="0.2"
importos,re,time,fnmatch,difflib
#FIXME:seehttp://stackoverflow.com/questions/4730121/cant-get-an-objects-class-name-in-python
RE_TYPE=type(re.compile(""))
classSearchAndReplace(object):
def__init__(self,search_path,search_string,replace_string,
search_only=True,file_filter=("*.*",)):
self.search_path=search_path
self.search_string=search_string
self.replace_string=replace_string
self.search_only=search_only
self.file_filter=file_filter
assertisinstance(self.file_filter,(list,tuple))
#FIXME:seehttp://stackoverflow.com/questions/4730121/cant-get-an-objects-class-name-in-python
self.is_re=isinstance(self.search_string,RE_TYPE)
print"Search'%s'in[%s]..."%(
self.search_string,self.search_path
)
print"_"*80
time_begin=time.time()
file_count=self.walk()
print"_"*80
print"%sfilessearchedin%0.2fsec."%(
file_count,(time.time()-time_begin)
)
defwalk(self):
file_count=0
forroot,dirlist,filelistinos.walk(self.search_path):
if".svn"inroot:
continue
forfilenameinfilelist:
forfile_filterinself.file_filter:
iffnmatch.fnmatch(filename,file_filter):
self.search_file(os.path.join(root,filename))
file_count+=1
returnfile_count
defsearch_file(self,filepath):
f=file(filepath,"r")
old_content=f.read()
f.close()
ifself.is_reorself.search_stringinold_content:
new_content=self.replace_content(old_content,filepath)
ifself.is_reandnew_content==old_content:
return
printfilepath
self.display_plaintext_diff(old_content,new_content)
defreplace_content(self,old_content,filepath):
ifself.is_re:
new_content=self.search_string.sub(self.replace_string,old_content)
ifnew_content==old_content:
returnold_content
else:
new_content=old_content.replace(
self.search_string,self.replace_string
)
ifself.search_only!=False:
returnnew_content
print"Writenewcontentinto%s..."%filepath,
try:
f=file(filepath,"w")
f.write(new_content)
f.close()
exceptIOError,msg:
print"Error:",msg
else:
print"OK"
print
returnnew_content
defdisplay_plaintext_diff(self,content1,content2):
"""
Displayadiff.
"""
content1=content1.splitlines()
content2=content2.splitlines()
diff=difflib.Differ().compare(content1,content2)
defis_diff_line(line):
forcharin("-","+","?"):
ifline.startswith(char):
returnTrue
returnFalse
print"line|text\n-------------------------------------------"
old_line=""
in_block=False
old_lineno=lineno=0
forlineindiff:
ifline.startswith("")orline.startswith("+"):
lineno+=1
ifold_lineno==lineno:
display_line="%4s|%s"%("",line.rstrip())
else:
display_line="%4s|%s"%(lineno,line.rstrip())
ifis_diff_line(line):
ifnotin_block:
print"..."
#Displaypreviousline
printold_line
in_block=True
printdisplay_line
else:
ifin_block:
#Displaythenextlineaberadiff-block
printdisplay_line
in_block=False
old_line=display_line
old_lineno=lineno
print"..."
if__name__=="__main__":
SearchAndReplace(
search_path=".",
#e.g.:simplestringreplace:
search_string='theoldstring',
replace_string='thenewstring',
#e.g.:Regularexpressionreplacing(usedre.sub)
#search_string=re.compile('{%url(.*?)%}'),
#replace_string="{%url'\g<1>'%}",
search_only=True,#Displayonlythedifference
#search_only=False,#writethenewcontent
file_filter=("*.py",),#fnmatch-Filter
)
希望本文所述对大家的Python程序设计有所帮助。