Commit f0a52c6a authored by insun park's avatar insun park
Browse files

docs: README, TODO, Makefile 및 진도 체크 시스템(progress_checker.py) 개선 및 추가

parent 978c6ed6
#!/usr/bin/env python3
"""
AI 전문가 양성 과정 - 학습 진도 체크 시스템
각 파트별 완료 상태를 추적하고 학습 진도를 시각화합니다.
"""
import json
import os
import sys
from datetime import datetime
from pathlib import Path
from typing import Dict, List, Optional
class ProgressChecker:
"""학습 진도 체크 및 관리 클래스"""
def __init__(self, progress_file: str = "learning_progress.json"):
self.progress_file = progress_file
self.progress_data = self._load_progress()
# 파트별 체크리스트 정의
self.checklists = {
"part_0": {
"name": "Introduction",
"items": [
"과정 소개 읽기",
"AI 역사 학습",
"개발 환경 설정",
"Git 기본 사용법",
"Jupyter Notebook 사용법"
]
},
"part_1": {
"name": "AI Development Environment",
"items": [
"Python 설치 및 설정",
"VSCode 설치 및 설정",
"가상환경 생성 및 사용",
"Poetry 설치 및 사용",
"Docker 기본 개념 이해"
]
},
"part_2": {
"name": "Python Core Syntax",
"items": [
"변수와 데이터 타입",
"연산자와 표현식",
"조건문과 반복문",
"함수 정의와 호출",
"예외 처리"
]
},
"part_3": {
"name": "Python Collections",
"items": [
"리스트와 튜플",
"딕셔너리와 세트",
"문자열 조작",
"컴프리헨션",
"collections 모듈"
]
},
"part_4": {
"name": "Object Oriented Programming",
"items": [
"클래스와 객체",
"상속과 다형성",
"캡슐화",
"매직 메서드",
"디자인 패턴 기초"
]
},
"part_5": {
"name": "AI Core Libraries",
"items": [
"NumPy 기본 사용법",
"Pandas 데이터 처리",
"Matplotlib 시각화",
"Scikit-learn 기초",
"데이터 전처리"
]
},
"part_6": {
"name": "Machine Learning",
"items": [
"지도학습 개념",
"비지도학습 개념",
"모델 평가 지표",
"하이퍼파라미터 튜닝",
"교차 검증"
]
},
"part_7": {
"name": "Deep Learning",
"items": [
"신경망 기초",
"PyTorch 사용법",
"CNN 구현",
"RNN/LSTM 구현",
"Transformer 이해"
]
},
"part_8": {
"name": "Model Serving with FastAPI",
"items": [
"FastAPI 기초",
"API 설계",
"모델 서빙",
"Pydantic 스키마",
"API 문서화"
]
},
"part_9": {
"name": "Production Ready API",
"items": [
"프로덕션 환경 설정",
"Docker 컨테이너화",
"로깅과 모니터링",
"보안 설정",
"성능 최적화"
]
},
"part_10": {
"name": "Expert Path",
"items": [
"AI 전문가 로드맵",
"추천 학습 자료",
"커리어 계획",
"포트폴리오 작성",
"네트워킹"
]
},
"part_11": {
"name": "MLOps",
"items": [
"MLOps 개념",
"CI/CD 파이프라인",
"모델 버전 관리",
"실험 추적",
"모델 모니터링"
]
},
"part_12": {
"name": "Model Optimization",
"items": [
"모델 경량화",
"양자화 기법",
"지식 증류",
"추론 최적화",
"하드웨어 가속"
]
},
"part_13": {
"name": "Generative AI",
"items": [
"생성형 AI 개념",
"LangChain 사용법",
"RAG 구현",
"AI 에이전트",
"프롬프트 엔지니어링"
]
},
"part_14": {
"name": "AI Ethics",
"items": [
"AI 윤리 개념",
"편향성 탐지",
"설명가능 AI",
"개인정보 보호",
"AI 거버넌스"
]
},
"part_15": {
"name": "Capstone Project",
"items": [
"프로젝트 기획",
"데이터 수집",
"모델 개발",
"API 구현",
"배포 및 발표"
]
}
}
def _load_progress(self) -> Dict:
"""진도 데이터 로드"""
if os.path.exists(self.progress_file):
try:
with open(self.progress_file, 'r', encoding='utf-8') as f:
return json.load(f)
except json.JSONDecodeError:
print(f"⚠️ {self.progress_file} 파일이 손상되었습니다. 새로 생성합니다.")
return {
"start_date": datetime.now().isoformat(),
"last_updated": datetime.now().isoformat(),
"parts": {}
}
def _save_progress(self):
"""진도 데이터 저장"""
self.progress_data["last_updated"] = datetime.now().isoformat()
with open(self.progress_file, 'w', encoding='utf-8') as f:
json.dump(self.progress_data, f, ensure_ascii=False, indent=2)
def mark_completed(self, part_id: str, item_index: int):
"""특정 항목을 완료로 표시"""
if part_id not in self.checklists:
print(f"❌ 알 수 없는 파트: {part_id}")
return
if part_id not in self.progress_data["parts"]:
self.progress_data["parts"][part_id] = {
"name": self.checklists[part_id]["name"],
"completed_items": [],
"start_date": datetime.now().isoformat(),
"completion_date": None
}
if item_index not in self.progress_data["parts"][part_id]["completed_items"]:
self.progress_data["parts"][part_id]["completed_items"].append(item_index)
self.progress_data["parts"][part_id]["completed_items"].sort()
# 모든 항목이 완료되면 완료 날짜 설정
if len(self.progress_data["parts"][part_id]["completed_items"]) == len(self.checklists[part_id]["items"]):
self.progress_data["parts"][part_id]["completion_date"] = datetime.now().isoformat()
self._save_progress()
print(f"✅ {self.checklists[part_id]['name']} - {self.checklists[part_id]['items'][item_index]} 완료!")
def mark_incomplete(self, part_id: str, item_index: int):
"""특정 항목을 미완료로 표시"""
if part_id in self.progress_data["parts"]:
if item_index in self.progress_data["parts"][part_id]["completed_items"]:
self.progress_data["parts"][part_id]["completed_items"].remove(item_index)
self._save_progress()
print(f"❌ {self.checklists[part_id]['name']} - {self.checklists[part_id]['items'][item_index]} 미완료로 변경")
def show_progress(self, part_id: Optional[str] = None):
"""진도 현황 표시"""
if part_id:
self._show_part_progress(part_id)
else:
self._show_overall_progress()
def _show_part_progress(self, part_id: str):
"""특정 파트의 진도 표시"""
if part_id not in self.checklists:
print(f"❌ 알 수 없는 파트: {part_id}")
return
checklist = self.checklists[part_id]
part_data = self.progress_data["parts"].get(part_id, {"completed_items": []})
print(f"\n📚 {checklist['name']} 진도 현황")
print("=" * 50)
completed_count = len(part_data["completed_items"])
total_count = len(checklist["items"])
progress_percent = (completed_count / total_count) * 100
print(f"진도: {completed_count}/{total_count} ({progress_percent:.1f}%)")
print()
for i, item in enumerate(checklist["items"]):
status = "✅" if i in part_data["completed_items"] else "⭕"
print(f"{status} {i+1:2d}. {item}")
if completed_count == total_count:
print(f"\n🎉 {checklist['name']} 완료!")
if part_data.get("completion_date"):
print(f"완료일: {part_data['completion_date'][:10]}")
def _show_overall_progress(self):
"""전체 진도 현황 표시"""
print("\n🚀 AI 전문가 양성 과정 - 전체 진도 현황")
print("=" * 60)
total_parts = len(self.checklists)
completed_parts = 0
total_items = 0
completed_items = 0
for part_id, checklist in self.checklists.items():
part_data = self.progress_data["parts"].get(part_id, {"completed_items": []})
part_completed = len(part_data["completed_items"])
part_total = len(checklist["items"])
total_items += part_total
completed_items += part_completed
if part_completed == part_total:
completed_parts += 1
progress_percent = (part_completed / part_total) * 100
status = "✅" if part_completed == part_total else "🔄"
print(f"{status} {checklist['name']:<25} {part_completed:2d}/{part_total:2d} ({progress_percent:5.1f}%)")
overall_progress = (completed_items / total_items) * 100
print("\n" + "=" * 60)
print(f"📊 전체 진도: {completed_parts}/{total_parts} 파트 완료 ({overall_progress:.1f}%)")
print(f"📈 완료된 항목: {completed_items}/{total_items}")
if completed_parts == total_parts:
print("\n🎉 축하합니다! 모든 파트를 완료하셨습니다!")
def reset_progress(self, part_id: Optional[str] = None):
"""진도 초기화"""
if part_id:
if part_id in self.progress_data["parts"]:
del self.progress_data["parts"][part_id]
self._save_progress()
print(f"🔄 {self.checklists[part_id]['name']} 진도가 초기화되었습니다.")
else:
self.progress_data["parts"] = {}
self._save_progress()
print("🔄 모든 진도가 초기화되었습니다.")
def export_progress(self, filename: str = "progress_report.md"):
"""진도 리포트 생성"""
with open(filename, 'w', encoding='utf-8') as f:
f.write("# AI 전문가 양성 과정 - 학습 진도 리포트\n\n")
f.write(f"생성일: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}\n\n")
total_items = 0
completed_items = 0
for part_id, checklist in self.checklists.items():
part_data = self.progress_data["parts"].get(part_id, {"completed_items": []})
part_completed = len(part_data["completed_items"])
part_total = len(checklist["items"])
total_items += part_total
completed_items += part_completed
progress_percent = (part_completed / part_total) * 100
status = "✅" if part_completed == part_total else "🔄"
f.write(f"## {status} {checklist['name']}\n\n")
f.write(f"진도: {part_completed}/{part_total} ({progress_percent:.1f}%)\n\n")
for i, item in enumerate(checklist["items"]):
item_status = "✅" if i in part_data["completed_items"] else "⭕"
f.write(f"- {item_status} {item}\n")
f.write("\n")
overall_progress = (completed_items / total_items) * 100
f.write(f"## 📊 전체 요약\n\n")
f.write(f"전체 진도: {completed_items}/{total_items} ({overall_progress:.1f}%)\n")
print(f"📄 진도 리포트가 {filename}에 저장되었습니다.")
def main():
"""메인 함수"""
checker = ProgressChecker()
if len(sys.argv) < 2:
print("사용법:")
print(" python progress_checker.py show [part_id] - 진도 현황 표시")
print(" python progress_checker.py complete part_id item_index - 항목 완료")
print(" python progress_checker.py incomplete part_id item_index - 항목 미완료")
print(" python progress_checker.py reset [part_id] - 진도 초기화")
print(" python progress_checker.py export [filename] - 진도 리포트 생성")
print("\n예시:")
print(" python progress_checker.py show")
print(" python progress_checker.py show part_2")
print(" python progress_checker.py complete part_2 0")
print(" python progress_checker.py export my_progress.md")
return
command = sys.argv[1]
if command == "show":
part_id = sys.argv[2] if len(sys.argv) > 2 else None
checker.show_progress(part_id)
elif command == "complete":
if len(sys.argv) < 4:
print("❌ 파트 ID와 항목 인덱스를 지정해주세요.")
return
part_id = sys.argv[2]
item_index = int(sys.argv[3])
checker.mark_completed(part_id, item_index)
elif command == "incomplete":
if len(sys.argv) < 4:
print("❌ 파트 ID와 항목 인덱스를 지정해주세요.")
return
part_id = sys.argv[2]
item_index = int(sys.argv[3])
checker.mark_incomplete(part_id, item_index)
elif command == "reset":
part_id = sys.argv[2] if len(sys.argv) > 2 else None
checker.reset_progress(part_id)
elif command == "export":
filename = sys.argv[2] if len(sys.argv) > 2 else "progress_report.md"
checker.export_progress(filename)
else:
print(f"❌ 알 수 없는 명령어: {command}")
if __name__ == "__main__":
main()
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment