python3.6, windows下
需求:
有一个新的版本的include目录中有一些头文件被更改(内容有修改,内容没有修改但位置有变更)
用Compare工具不能很好的比较出头文件中内容位置变更的文件,此时用python可以进行比较
实现:
#!/usr/bin/python
# -*- coding: utf-8 -*-
import os,re,shutil,sys
src_dir = 'C:\\Users\\Administrator\\Desktop\\tmp\\1'
dest_dir ='C:\\Users\\Administrator\\Desktop\\tmp\\2'
res_file = 'C:\\Users\\Administrator\\Desktop\\tmp\\diff.txt'
def ListAllFile(dir):
"""
返回目录下所有的文件名
:param data: dir 文件夹
:return 所有文件
"""
files=[]
list = os.listdir(dir)
for i in range(0, len(list)):
path = os.path.join(dir, list[i])
if os.path.isdir(path):
files.extend(ListAllFile(path))
elif os.path.isfile(path) and path.endswith('.h'):
files.append(path)
return files
def InitHeaderFile(filename):
"""
针对头文件中有嵌套类,将一个class看做一个层级,嵌套类属于下一个层级
#include<> 层级0,
class A { 层级1,
xxxA
class B{层级2,
xxxB
};
class C{层级2
xxxc
};
};
:param data: filename 头文件名
:return dict字典 "0":["#include<>"], "1":["class A {", "};"]
"""
try:
with open(filename) as f:
lines = f.readlines()
i = 0
dict = {}
for line in lines:
line = line.strip()
class_end = False
if line == '':
continue
if line.endswith('{'):
i = i + 1
elif line.startswith('}'):
i = i - 1
class_end = True
if i not in dict:
tmp = []
tmp.append(line)
dict[i] = tmp
else:
if not class_end:
dict[i].append(line)
else:
dict[i+1].append(line)
return dict
except Exception:
raise RuntimeError('open [%s] failed'% filename)
def CheckHeaderSame1(src_dict, dest_dict):
'''
该函数针对头文件中的类存在嵌套类,且类的格式如下:
class Test { // 类的开头行以'{'结尾
xxx
void func{
} 类中如果有函数实现,也必须是函数声明行以'{'结尾,函数结束以'}'开头
}; // 类的结尾行以'}'开头
:param data: src_dict, dest_dict 经过InitHeaderFile得到的字典
:return 返回比较结果
'''
for k, v in src_dict.items():
if k not in dest_dict:
return False
for line in v:
if line not in dest_dict[k]:
return False
return True
def CheckHeaderSame2(src_file, dest_file):
'''
该函数针对头文件中除空行外不存在相同行的情况
:param data:src_file,dest_file要比较的头文件
:return 返回比较结果
'''
src_lines = {}
dest_lines = {}
try:
with open(src_file, 'r') as f:
for line in f:
src_lines[line.strip()] = None
except Exception:
raise RuntimeError('open [%s] failed'% src_file)
try:
with open(dest_file, 'r') as f:
for line in f:
dest_lines[line.strip()] = None
except Exception:
raise RuntimeError('open [%s] failed'% dest_file)
for key in src_lines:
if key not in dest_lines:
return False
return True
if __name__ == "__main__":
src_files = ListAllFile(src_dir)
dest_files = ListAllFile(dest_dir)
diff_files = []
for src_file in src_files:
raw_file = src_file.split('\\')[-1]
for dest_file in dest_files:
if dest_file.split('\\')[-1] == raw_file:
src_dict = InitHeaderFile(src_file)
dest_dict = InitHeaderFile(dest_file)
if not CheckHeaderSame1(src_dict, dest_dict):
diff_files.append(src_file)
print('Different file: ' + src_file)
else:
print('Same file: ' + src_file)
try:
with open(res_file, 'a+') as f:
for file in diff_files:
f.write(src_file)
f.write('\n')
except Exception:
raise RuntimeError('open [%s] failed'% res_file)
执行结果:
比较结果会保存到diff.txt中