185 lines
6.3 KiB
Python
185 lines
6.3 KiB
Python
#!/usr/bin/env python
|
|
# -*- coding: utf-8 -*-
|
|
"""
|
|
全面检查 ARTv2 代码中的变量作用域问题
|
|
"""
|
|
|
|
import os
|
|
import re
|
|
|
|
def check_if_scope_issues(file_path):
|
|
"""检查 if 语句中定义的变量在外部使用的问题"""
|
|
issues = []
|
|
|
|
with open(file_path, 'r', encoding='utf-8', errors='ignore') as f:
|
|
content = f.read()
|
|
lines = content.splitlines()
|
|
|
|
# 检查常见的作用域问题模式
|
|
patterns = [
|
|
# 在 if 块中定义变量,然后在外部使用
|
|
(r'if\s+.*:\s*\n\s+(\w+)\s*=', 'Variable defined in if block'),
|
|
# 在 for 循环中定义变量,然后在外部使用
|
|
(r'for\s+(\w+)\s+in\s+.*:\s*\n.*\n.*\1', 'Variable from for loop used outside'),
|
|
]
|
|
|
|
for i, line in enumerate(lines, 1):
|
|
# 检查未初始化的变量
|
|
if re.search(r'^\s*if\s+.*:\s*$', line):
|
|
# 查找 if 块中定义的变量
|
|
indent = len(line) - len(line.lstrip())
|
|
j = i
|
|
if_vars = []
|
|
|
|
while j < len(lines):
|
|
next_line = lines[j]
|
|
next_indent = len(next_line) - len(next_line.lstrip())
|
|
|
|
if next_line.strip() and next_indent <= indent:
|
|
break
|
|
|
|
# 查找变量赋值
|
|
match = re.match(r'\s*(\w+)\s*=', next_line)
|
|
if match and next_indent > indent:
|
|
var_name = match.group(1)
|
|
if var_name not in ['self', 'cls']:
|
|
if_vars.append((var_name, j + 1))
|
|
|
|
j += 1
|
|
|
|
# 检查这些变量是否在 if 块外使用但没有初始化
|
|
if if_vars:
|
|
for var_name, def_line in if_vars:
|
|
# 检查变量是否在 if 之前初始化
|
|
initialized = False
|
|
for k in range(max(0, i - 20), i):
|
|
if re.search(r'\b' + var_name + r'\s*=', lines[k]):
|
|
initialized = True
|
|
break
|
|
|
|
if not initialized:
|
|
# 检查是否在 if 块外使用
|
|
for k in range(j, min(len(lines), j + 20)):
|
|
if re.search(r'\b' + var_name + r'\b', lines[k]):
|
|
issues.append({
|
|
'line': def_line,
|
|
'usage_line': k + 1,
|
|
'code': lines[def_line - 1].strip(),
|
|
'variable': var_name,
|
|
'type': 'if_scope'
|
|
})
|
|
break
|
|
|
|
return issues
|
|
|
|
def check_try_except_issues(file_path):
|
|
"""检查 try-except 块中的变量作用域问题"""
|
|
issues = []
|
|
|
|
with open(file_path, 'r', encoding='utf-8', errors='ignore') as f:
|
|
lines = f.readlines()
|
|
|
|
in_try = False
|
|
in_except = False
|
|
try_vars = []
|
|
try_indent = 0
|
|
except_indent = 0
|
|
|
|
for i, line in enumerate(lines, 1):
|
|
stripped = line.lstrip()
|
|
if not stripped or stripped.startswith('#'):
|
|
continue
|
|
|
|
indent = len(line) - len(stripped)
|
|
|
|
# 检测 try 块
|
|
if re.match(r'try:', stripped):
|
|
in_try = True
|
|
try_indent = indent
|
|
try_vars = []
|
|
continue
|
|
|
|
# 检测 except 块
|
|
if re.match(r'except.*:', stripped):
|
|
in_except = True
|
|
except_indent = indent
|
|
continue
|
|
|
|
# 在 try 块中收集变量定义
|
|
if in_try and indent > try_indent:
|
|
match = re.match(r'(\w+)\s*=', stripped)
|
|
if match:
|
|
var_name = match.group(1)
|
|
if var_name not in ['self', 'cls']:
|
|
try_vars.append(var_name)
|
|
|
|
# 检测退出 try-except 块
|
|
if (in_try or in_except) and stripped and indent <= try_indent:
|
|
# 检查 try 块中定义的变量是否在外部使用
|
|
for var_name in try_vars:
|
|
if re.search(r'\b' + var_name + r'\b', stripped):
|
|
issues.append({
|
|
'line': i,
|
|
'code': line.rstrip(),
|
|
'variable': var_name,
|
|
'type': 'try_scope'
|
|
})
|
|
in_try = False
|
|
in_except = False
|
|
try_vars = []
|
|
|
|
return issues
|
|
|
|
def main():
|
|
"""主函数"""
|
|
script_dir = os.path.dirname(os.path.abspath(__file__))
|
|
core_scripts = os.path.join(script_dir, 'Core', 'Scripts')
|
|
|
|
print("=" * 70)
|
|
print("ARTv2 变量作用域全面检查")
|
|
print("=" * 70)
|
|
print()
|
|
|
|
total_files = 0
|
|
total_issues = 0
|
|
issue_files = []
|
|
|
|
for root, dirs, files in os.walk(core_scripts):
|
|
for filename in files:
|
|
if filename.endswith('.py'):
|
|
total_files += 1
|
|
file_path = os.path.join(root, filename)
|
|
rel_path = os.path.relpath(file_path, script_dir)
|
|
|
|
# 检查 if 作用域问题
|
|
if_issues = check_if_scope_issues(file_path)
|
|
|
|
# 检查 try-except 作用域问题
|
|
try_issues = check_try_except_issues(file_path)
|
|
|
|
all_issues = if_issues + try_issues
|
|
|
|
if all_issues:
|
|
total_issues += len(all_issues)
|
|
issue_files.append((rel_path, all_issues))
|
|
|
|
if issue_files:
|
|
print(f"⚠️ 发现 {total_issues} 个潜在的变量作用域问题:\n")
|
|
for file_path, issues in issue_files:
|
|
print(f"📁 {file_path}")
|
|
for issue in issues:
|
|
print(f" Line {issue['line']}: {issue['code'][:60]}")
|
|
print(f" 类型: {issue['type']}, 变量: '{issue['variable']}'")
|
|
print()
|
|
|
|
print("=" * 70)
|
|
print(f"检查完成: 扫描了 {total_files} 个文件")
|
|
if total_issues == 0:
|
|
print("✅ 未发现明显的变量作用域问题")
|
|
else:
|
|
print(f"⚠️ 发现 {total_issues} 个潜在问题(可能包含误报)")
|
|
print("=" * 70)
|
|
|
|
if __name__ == '__main__':
|
|
main()
|