Files
Aislo/resources/tester/scratch/fix_maint_worker_rows.py
T

143 lines
6.0 KiB
Python

import os, sys, re
sys.stdout.reconfigure(encoding='utf-8')
base_dir = "resources/knowledge/original/원가계산/건설공사_표준품셈/05_유지관리부문"
job_words = [
"포장공", "보통인부", "특별인부", "철근공", "보링공", "기계설비공", "철공", "조경공",
"착암공", "용접공", "배관공", "할석공", "석공", "줄눈공", "미장공", "도장공", "방수공",
"타일공", "내장공", "석면해체공", "궤도공", "중급기술자", "초급기술자", "고급기술자"
]
files = [
"제1장_공통.md",
"제2장_토목.md",
"제3장_건축.md",
"제4장_기계설비.md"
]
total_fixed = 0
for fname in files:
fpath = os.path.join(base_dir, fname)
with open(fpath, 'r', encoding='utf-8') as f:
lines = f.readlines()
new_lines = []
file_fixes = 0
for idx, line in enumerate(lines):
line_str = line.strip()
if not (line_str.startswith('|') and line_str.endswith('|')):
new_lines.append(line)
continue
cells = [c.strip() for c in line_str.split('|')[1:-1]]
# Skip divider or note
if all(re.match(r'^:?-+:?$', c) for c in cells if c) or (cells and cells[0] in ["비고", "비 고", "주", "[주]"]):
new_lines.append(line)
continue
# Find which cell has multiple job titles
job_cell_idx = -1
detected_jobs = []
for c_idx, c in enumerate(cells):
# Check if this cell contains multiple known job words
# Notice in markdown it may be spaced: "철 근 공 보 통 인 부"
# Normalize spaces inside tokens
# Split tokens:
toks = c.split()
# If tokens end with common job characters
if len(toks) >= 2 and all(any(tok.endswith(end) for end in ["공", "부", "사", "자"]) for tok in toks):
# Candidate job cell
# Check if next cells have matching "인 인..." and numbers
job_cell_idx = c_idx
detected_jobs = toks
break
# Also handle spaced letters like "포 장 공 보 통 인 부"
# Combine characters and match
c_nospace = c.replace(" ", "")
matched_jobs = []
cur_str = c_nospace
for jw in sorted(job_words, key=len, reverse=True):
while jw in cur_str:
matched_jobs.append(jw)
cur_str = cur_str.replace(jw, "", 1)
if len(matched_jobs) >= 2 and cur_str == "":
# Reconstruct in order of original string
ordered_jobs = []
pos = 0
while pos < len(c_nospace):
found = False
for jw in sorted(job_words, key=len, reverse=True):
if c_nospace[pos:].startswith(jw):
ordered_jobs.append(jw)
pos += len(jw)
found = True
break
if not found:
break
if len(ordered_jobs) >= 2:
job_cell_idx = c_idx
detected_jobs = ordered_jobs
break
if job_cell_idx != -1 and len(detected_jobs) >= 2:
N = len(detected_jobs)
# Find unit cell and qty cell
unit_cell_idx = -1
qty_cell_idx = -1
for c_idx in range(job_cell_idx + 1, len(cells)):
toks = cells[c_idx].split()
if len(toks) == N and all(t in ["인", "대", "hr", "시간", "식", "-"] for t in toks):
unit_cell_idx = c_idx
break
if unit_cell_idx != -1:
# Find qty cell(s)
# Check if there are columns with N numbers
can_split = False
col_splits = {} # c_idx -> list of N values
for c_idx in range(unit_cell_idx + 1, len(cells)):
toks = cells[c_idx].split()
if len(toks) == N and all(re.match(r'^-?\d+(?:,\d+)?(?:\.\d+)?$', t) for t in toks):
col_splits[c_idx] = toks
can_split = True
if can_split:
# Generate N rows
# In other cells, first row gets the cell value, other rows get empty ""
unit_toks = cells[unit_cell_idx].split()
for r_idx in range(N):
new_row_cells = []
for c_idx in range(len(cells)):
if c_idx == job_cell_idx:
new_row_cells.append(detected_jobs[r_idx])
elif c_idx == unit_cell_idx:
new_row_cells.append(unit_toks[r_idx])
elif c_idx in col_splits:
new_row_cells.append(col_splits[c_idx][r_idx])
else:
# First row keeps existing value, subsequent rows get empty string
if r_idx == 0:
new_row_cells.append(cells[c_idx])
else:
new_row_cells.append("")
new_line_str = "| " + " | ".join(new_row_cells) + " |\n"
new_lines.append(new_line_str)
file_fixes += 1
total_fixed += 1
continue
new_lines.append(line)
if file_fixes > 0:
print(f"{fname}: fixed {file_fixes} multi-worker squashed rows")
with open(fpath, 'w', encoding='utf-8') as f:
f.writelines(new_lines)
print(f"Total multi-worker rows fixed in 유지관리부문: {total_fixed}")