|
- https://cafe.daum.net/dddowny/c4Du/2
https://kind-slip-86b.notion.site/2024-10-04-2b1dbfb3486742cf98089c92ff5b21c8
++++
conda channel
-> conda를 통해 패키지 관리 및 가상환경 관리를 할 때, channel을 통해 어디서 패키지를 가져와 설치할지를 지정할 수 있음.
패키지들이 저장되어 있으면서 호스팅 되는 위치
conda config --add channels conda-forge : channel을 conda-forge(여러 자발적인 기여자들이 모인 커뮤니티에서 운영 및 관리하는 conda용 채널)를 추가함.
conda config --set channel_priority strict : 우선 순위가 높은 채널에서만 패키지 설치, 원하는 채널에서만 설치할 수 있게 함.
conda config --remove channels defaults : 디폴트 채널을 삭제함.
conda-forge 사용하는 이유 : conda의 기본 채널보다 머신 러닝이나 컴퓨터 비전 등 개발에 다양하고 안정적인 패키지들 제공함.
- 원하는 패키지가 conda-forge에서 안 보인다면 pip 사용.
https://error-note.tistory.com/28
데이터셋 구성은 test, train인데 train 폴더에서 val (검증) 폴더 데이터셋을 대회 참가자가 결정하여 나누라고 함.
-> 파이썬 코드를 통해 데이터를 8:2로 나눔.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 | import os import random import shutil # 데이터셋 경로 images_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/origin/images" # 이미지 파일들이 있는 경로 labels_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/origin/labels" # 라벨 파일들이 있는 경로 # 데이터셋을 저장할 train과 val 폴더 경로 train_images_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/train/images" train_labels_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/train/labels" val_images_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/val/images" val_labels_dir = "D:/MINSEO/ultralytics/datasets/TLD_2024/val/labels" # train과 val 비율 설정 train_ratio = 0.8 # 이미지와 라벨 파일 목록 얻기 image_files = sorted([f for f in os.listdir(images_dir) if f.endswith(".jpg")]) # 이미지 파일이 .jpg일 경우 label_files = sorted([f for f in os.listdir(labels_dir) if f.endswith(".txt")]) # 라벨 파일이 .txt일 경우 # 이미지와 라벨 파일 일치 여부 확인 (파일명이 동일한지 확인) assert len(image_files) == len(label_files), "이미지와 라벨 파일 개수가 일치하지 않습니다." for img_file, lbl_file in zip(image_files, label_files): assert os.path.splitext(img_file)[0] == os.path.splitext(lbl_file)[0], f"{img_file}와 {lbl_file}의 이름이 일치하지 않습니다." # 데이터 랜덤 섞기 combined = list(zip(image_files, label_files)) random.shuffle(combined) # train과 val로 나누기 train_size = int(len(combined) * train_ratio) train_data = combined[:train_size] val_data = combined[train_size:] # train 폴더에 데이터 복사 os.makedirs(train_images_dir, exist_ok=True) os.makedirs(train_labels_dir, exist_ok=True) for img_file, lbl_file in train_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(train_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(train_labels_dir, lbl_file)) # val 폴더에 데이터 복사 os.makedirs(val_images_dir, exist_ok=True) os.makedirs(val_labels_dir, exist_ok=True) for img_file, lbl_file in val_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(val_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(val_labels_dir, lbl_file)) print("데이터셋 분할이 완료되었습니다.") | cs |
학습을 돌리는데 성공, 메모리 부족 경고와 학습 시간이 너무 오래 걸리는 현상 발생.
데이터셋 구성 확인 결과 중복되는 이미지들이 많고 크기가 다 다름.
배치 사이즈를 2로 바꾼 결과 메모리도 반절로 줄어들어 나타나게 됨, imgsz 변경 -> 640으로 규모 변경 (차이 없음 확인)
시간은 줄어들었지만 메모리 부족 경고는 계속 뜸.
데이터셋 25%만 사용, 메모리 부족 경고도 사라짐.
훈련 완료된 모습
++ bus_noSign과 bus_warning의 이미지 개수가 적은 점과 정확도가 0으로 나오는 것
이미지 자체가 너무 적어서 학습이 어려운가 확인, 클래스 번호가 11이랑 13 나올 때마다 카운트 함.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | import os # 폴더 경로를 지정 folder_path = r"D:\MINSEO\ultralytics\datasets\TLD_2024\origin\labels" # 카운트 변수를 초기화 a = 0 b = 0 # 폴더 내의 모든 파일을 확인 for filename in os.listdir(folder_path): if filename.endswith('.txt'): # 텍스트 파일을 열어서 처리 file_path = os.path.join(folder_path, filename) with open(file_path, 'r') as file: for line in file: # 공백을 기준으로 분리하고 첫 번째 항목을 확인 first_number = line.split()[0] if first_number == '11': a += 1 elif first_number == '13': b += 1 # 결과 출력 print(f"11의 총 카운트 (a): {a}") # bus_noSign print(f"13의 총 카운트 (b): {b}") # bus_warning | cs |
결과 이미지 개수가 원래 적은 거 확인.
데이터셋 나누는 작업, 4폴더로 나눔
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 | import os import random import shutil # 데이터셋 경로 images_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\origin\images" # 이미지 파일들이 있는 경로 labels_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\origin\labels" # 라벨 파일들이 있는 경로 # 데이터셋을 저장할 폴더 경로 dataset1_images_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset1\images" dataset1_labels_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset1\labels" dataset2_images_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset2\images" dataset2_labels_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset2\labels" dataset3_images_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset3\images" dataset3_labels_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset3\labels" dataset4_images_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset4\images" dataset4_labels_dir = r"D:\MINSEO\ultralytics\datasets\TLD_2024\dataset4\labels" image_files = sorted([f for f in os.listdir(images_dir) if f.endswith(".jpg")]) # .jpg label_files = sorted([f for f in os.listdir(labels_dir) if f.endswith(".txt")]) #파일 일치 여부 확인 assert len(image_files) == len(label_files), "이미지와 라벨 파일 개수가 일치하지 않습니다." for img_file, lbl_file in zip(image_files, label_files): assert os.path.splitext(img_file)[0] == os.path.splitext(lbl_file)[0], f"{img_file}와 {lbl_file}의 이름이 일치하지 않습니다." combined = list(zip(image_files, label_files)) random.shuffle(combined) total_size = len(combined) dataset_size = total_size // 4 dataset1_data = combined[:dataset_size] dataset2_data = combined[dataset_size:dataset_size * 2] dataset3_data = combined[dataset_size * 2:dataset_size * 3] dataset4_data = combined[dataset_size * 3:] # dataset1 os.makedirs(dataset1_images_dir, exist_ok=True) os.makedirs(dataset1_labels_dir, exist_ok=True) for img_file, lbl_file in dataset1_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(dataset1_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(dataset1_labels_dir, lbl_file)) print(f"Dataset 1: {img_file} -> {dataset1_images_dir}, {lbl_file} -> {dataset1_labels_dir}") # dataset2 os.makedirs(dataset2_images_dir, exist_ok=True) os.makedirs(dataset2_labels_dir, exist_ok=True) for img_file, lbl_file in dataset2_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(dataset2_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(dataset2_labels_dir, lbl_file)) print(f"Dataset 2: {img_file} -> {dataset2_images_dir}, {lbl_file} -> {dataset2_labels_dir}") # dataset3 os.makedirs(dataset3_images_dir, exist_ok=True) os.makedirs(dataset3_labels_dir, exist_ok=True) for img_file, lbl_file in dataset3_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(dataset3_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(dataset3_labels_dir, lbl_file)) print(f"Dataset 3: {img_file} -> {dataset3_images_dir}, {lbl_file} -> {dataset3_labels_dir}") # dataset4 os.makedirs(dataset4_images_dir, exist_ok=True) os.makedirs(dataset4_labels_dir, exist_ok=True) for img_file, lbl_file in dataset4_data: shutil.copy(os.path.join(images_dir, img_file), os.path.join(dataset4_images_dir, img_file)) shutil.copy(os.path.join(labels_dir, lbl_file), os.path.join(dataset4_labels_dir, lbl_file)) print(f"Dataset 4: {img_file} -> {dataset4_images_dir}, {lbl_file} -> {dataset4_labels_dir}") | cs |
이 다음에 똑같이 dataset n번마다 train이랑 val을 또 나누어서 폴더 분리함
나눈 데이터셋을 분리시켜서 학습을 시킬 예정.
데이터셋을 혼합하여 나누고 학습을 이어서 진행하는 형식.
학습시킨 모델에 이어서 추가적인 학습을 진행하게 됨.
가장 최신 yolo11 pt파일 받아서 훈련 진행해봄
https://docs.ultralytics.com/models/yolo11/#supported-tasks-and-modes
훈련 결과
첫댓글 데이터셋 분할할때 클래스별로 객체의 갯수를 고려하여 분할해야할듯
마지막 출력결과에 보면 bus_nosign 클래스는 2장만 사용했고 bus_warning 3장만 사용되었음 정확도도 0점임
모든 클래스의 갯수가 비슷하도록 훈련데이터를 구성하는게 필요함
넵 확인했습니다!