이 글은 Today I Learn 시리즈의 234번째 기록입니다. (총 235개)

사전에 없는 말 하나가 곡 100개를 감췄다

둘러보기에서 분위기와 장르를 고르면 결과가 한두 곡뿐인 조합이 있었다. 곡이 모자란 줄 알고 세어 보다가 다른 걸 찾았다. 승인한 744곡 중 100곡에 장르가 아예 안 붙어 있었다.

전부 솔로 피아노 계열이었다. 프롬프트에 「인상주의」·「드뷔시풍」·「호텔 로비 그랜드 피아노」 같은 말이 적혀 있는데, 프롬프트에서 장르를 뽑는 사전에는 클래식으로 걸리는 말이 세 개(클래식·오케스트라·실내악)뿐이었다. 그래서 아무 데도 안 걸렸다.

앞선 TIL 8에서도 사전이 좁으면 걸릴 곡을 놓친다고 적었다. 그때는 「활기」에 단어를 더 넣자 놓치던 곡이 걸린 이야기였다. 이번에 하나 더 배운 건 빠진 결과가 「덜 걸린다」가 아니라 「한 축에서 아예 안 보인다」였다는 것이다. 그 100곡은 분위기와 편성은 붙어 있어서 다른 화면에서는 정상으로 보였다. 장르로 찾을 때만 존재하지 않았다.

빈칸은 화면에서 눈에 띄지 않는다. 무언가를 자동으로 채우는 자리에서는 「무엇이 잘못 붙었나」만 보지 말고 「아무것도 안 붙은 게 몇 개인가」를 따로 세어 봐야 한다. 그 수가 0이 아니면 그것들은 어느 화면에서는 없는 것이다.


라운지라는 칸을 새로 만들까 했다

이 100곡을 어느 장르로 볼지 정해야 했다. 51곡이 「호텔 로비 그랜드 피아노」였으니 「라운지」 칸을 만들면 깔끔해 보였다.

만들지 않기로 했다. 라운지는 어디에 트느냐지 무슨 음악이냐가 아니다. 룸톤에는 업종 축이 따로 있어서 호텔·라운지는 거기서 다룬다. 장르 축에 용도를 섞으면 나중에 같은 곡을 두 축에서 두 번 고르게 되고, 「라운지에서 트는 재즈」는 어디에 들어가야 하는지 답이 없어진다.

그래서 그 51곡은 뉴에이지로 넣었다. 컨템포러리 솔로 피아노가 보통 그 칸이다. 사전에 말을 넣을 때도 「호텔 로비」는 빼고 편성 말인 「솔로 그랜드 피아노」로 잡게 했다. 용도 말을 사전에 넣으면 재즈 편성의 호텔 로비 곡까지 뉴에이지로 끌려간다.

분류 칸을 새로 만들기 전에 그 이름이 대상의 성격인지 쓰임인지를 먼저 가린다. 쓰임이면 다른 축에 이미 자리가 있을 확률이 높다.


칸 하나를 늘렸더니 얇은 조합이 다섯 개 늘었다

같은 자리에서 한 곡짜리 묶음도 있었다. 파리 카페 뮈제트 왈츠 한 곡이다. 월드라는 칸이 있으면 거기, 없으면 클래식으로 하기로 했는데 없는 칸이 새로 만들어졌다.

조합을 세 보니 한 자리 조합이 10개에서 15개로 늘어 있었다. 늘어난 다섯 개가 전부 그 한 곡이 만든 것이었다. 그 곡이 분위기를 다섯 개 갖고 있으니, 그 곡만 있는 장르는 분위기와 만나는 자리마다 1곡짜리 조합이 된다. 얇은 조합을 줄이려고 시작한 일이 얇은 조합을 늘린 셈이다.

되돌리고 그 곡을 클래식에 넣자 12개로 돌아왔다.

고르는 칸이 하나 늘어나는 비용은 그 칸 하나가 아니다. 다른 축과 곱해진 만큼이다. 축이 둘이면 칸 하나가 조합 여러 개가 되고, 그 조합에 든 것이 한두 개면 고른 사람에게는 빈 화면으로 보인다. 칸을 만들 때 「이 칸에 몇 개가 들어가나」와 함께 「이 칸이 다른 축과 만나 몇 개의 조합이 되나」를 센다.


공백은 메웠는데 문제는 그대로였다

100곡에 장르를 붙이고 다시 셌다. 장르 없는 곡은 0이 됐고, 고를 수 있는 조합은 83개에서 89개로 늘었다. 그런데 처음에 고치려던 것, 결과가 한 자리인 조합은 10개에서 12개로 줄지 않았다.

남은 열 개는 앰비언트(34곡)와 보사노바의 비주류 분위기, 클래식 주변 분위기였다. 곡 수 자체가 적은 자리다. 분류를 고쳐도 없는 곡이 생기지는 않는다.

여기서 남는 건 「헛일이었다」가 아니다. 두 문제가 한 증상으로 보였을 뿐이라는 것이다. 하나는 분류의 공백이고 하나는 재고의 부족이다. 증상(얇은 조합)을 보고 시작했더니 먼저 해결된 건 눈에 안 보이던 쪽이었고, 원래 눈에 보였던 쪽은 곡을 더 만들어야 한다.

무언가를 고치기 전에 「이 증상이 원인 하나에서 나온 게 맞나」를 묻는 편이 낫다. 아니면 고치고 나서 숫자가 안 움직이는 것을 보고 실패로 오해한다.


묻지 않아도 되는 것을 묻고 있었다

다른 이야기 하나. 곡을 반입하는 도구가 곡마다 「이 곡에 목소리가 있나」를 물었다. 앞선 TIL 17에서 자동 검사를 끄고 사람이 고르게 바꾼 자리다. 자동 검사가 일부 악기를 목소리로 착각했으니 사람이 낫다고 본 것이다.

그런데 이번에 보니 그 질문 자체가 필요 없었다. 가사가 들리는 곡은 곡을 고르는 단계에서 애초에 받지 않는다. 그러니 반입되는 곡은 전부 가사가 없다. 늘 같은 답이 나오는 질문을 곡마다 묻고 있었던 것이다.

그래서 물음을 지웠다. 자동 검사를 끈 것이 한 걸음이었고, 사람에게 묻는 것까지 뺀 것이 그다음 걸음이었다.

자동화를 손볼 때 「기계가 할지 사람이 할지」로만 생각하기 쉽다. 그 앞에 물음이 하나 더 있다. 이 판단이 애초에 필요한가. 들어오는 것이 한 가지뿐이면 그걸 가르는 일은 기계가 해도 사람이 해도 낭비다.


요약

  • 자동 분류를 볼 때 「잘못 붙은 것」만 보지 말고 「아무것도 안 붙은 것」을 따로 센다. 그것들은 어느 화면에서는 존재하지 않는다.
  • 분류 칸을 만들기 전에 그 이름이 대상의 성격인지 쓰임인지 가린다. 쓰임이면 다른 축에 자리가 있다.
  • 칸 하나를 늘리는 비용은 다른 축과 곱해진 만큼이다. 한 개짜리 칸은 만들지 않는다.
  • 한 증상이 원인 하나에서 나왔다고 가정하지 않는다. 고치고 숫자가 안 움직이면 다른 원인이 남아 있는 것이다.
  • 사람에게 물을지 기계에 맡길지 앞에 「이 판단이 애초에 필요한가」가 있다. 늘 같은 답이 나오는 질문은 지운다.

Series: Today I Learn

1 | C++ 자료형(Data Type) 2 | MD5 vs pHash 3 | C++에서 함수의 선언과 정의 4 | Tkinter padx, pady 5 | 메모리와 포인터 변수 6 | Call by Value, Call by Reference, Call by Pointer 비교 7 | const 8 | Gemfile — Jekyll 프로젝트의 의존성 파일 9 | kramdown-parser-gfm — Jekyll의 GFM 파서 10 | 파서(Parser) 11 | AHU vs OHU 12 | I might try it vs I'll try it 뉘앙스 차이 13 | SESSION_EXPIRE_AT_BROWSER_CLOSE=True 14 | configuration key 15 | Git stash vs discard 16 | subprocess.Popen으로 Windows 탐색기에 명령어를 전달 17 | Post 잔디 분석하기 18 | Google Sheets Sync 최적화 19 | DSL (Domain Specific Language)과 GPL (General Purpose Language) 20 | 마크다운 표 그리는 방법 21 | 쿼리 파라미터(Query Parameter). 기존 QR코드 재활용 22 | Django 보안 취약점 점검 및 수정 23 | OOP Object-Oriented Programming 객체 지향 프로그래밍 24 | Fernet 대칭 암호화 25 | Jekyll 코드블록 안의 Liquid 태그 26 | 습관만들기 Pawbit TIL 1 27 | insertOnConflictUpdate vs DoUpdate(target) 28 | 세션 필터 29 | 아코디언(Accordiaon) UI를 펼친상태로 만들기 30 | input의 step 31 | 습관만들기 Pawbit TIL 2 32 | 습관만들기 Pawbit TIL 3 33 | Word Cloud 34 | Google Sheets를 데이터 버스로(with AppSheet) 35 | Django 모델 텍스트 필드 자동 수집 패턴 36 | localStorage로 섹션 토글 상태 유지 37 | 순차 ID 생성(`select_for_update()` + `max()` 조합) 38 | 역참조 검색과 distinct() 39 | xlsx 다운로드와 로딩 오버레이 충돌 40 | Android 파일 공유 MIME 타입 41 | AssetManifest — Flutter 빌드 타임 asset 목록 런타임 조회 42 | 크레센도 Phaser + TypeScript TIL 1 43 | 크레센도 Phaser + TypeScript TIL 2 44 | 크레센도 Phaser + TypeScript TIL 3 45 | 크레센도 Phaser + TypeScript TIL 4 46 | 크레센도 Phaser + TypeScript TIL 5 47 | 여둘까 Office Layout TIL 1 48 | 습관만들기 Pawbit TIL 4 49 | 여둘까 Office Layout TIL 2 50 | 여둘까 Office Layout TIL 3 51 | 크레센도 Phaser + TypeScript TIL 6 52 | UTF-8 BOM과 PowerShell 파일 쓰기 53 | 소리꽃 KeyBloom TIL 1 54 | 습관만들기 Pawbit TIL 5 55 | 여둘까 Office Layout TIL 4 56 | 소리꽃 KeyBloom TIL 2 57 | 소리꽃 KeyBloom TIL 3 58 | 메트로놈 Simple Metronome TIL 1 59 | 소리꽃 KeyBloom TIL 4 60 | 메트로놈 Simple Metronome TIL 2 61 | 소리꽃 KeyBloom TIL 5 62 | 습관만들기 Pawbit TIL 6 63 | 크레센도 Phaser + TypeScript TIL 7 64 | 메트로놈 Simple Metronome TIL 3 65 | 소설 타임라인 관리 도구 Lumior TIL 1 66 | 습관만들기 Pawbit TIL 7 67 | 정적 블로그 SEO 정비와 Pagefind 검색 도입 68 | 크레센도 Phaser + TypeScript TIL 8 69 | 메트로놈 Simple Metronome TIL 4 70 | 습관만들기 Pawbit TIL 8 71 | 안드로이드 AudioTrack 연속 재생, 실측 피커 정렬, 카메라 토치 플래시 72 | 메트로놈 Simple Metronome TIL 5 73 | 모래게임 Sandrop TIL 1 74 | 습관만들기 Pawbit TIL 9 75 | 메트로놈 Simple Metronome TIL 6 76 | 모래게임 Sandrop TIL 2 77 | 모래게임 Sandrop TIL 3 78 | 습관만들기 Pawbit TIL 10 79 | 습관만들기 Pawbit TIL 11 80 | 메트로놈 Simple Metronome TIL 7 81 | 모래게임 Sandrop TIL 4 82 | 모래게임 Sandrop TIL 5 83 | 습관만들기 Pawbit TIL 12 84 | 모래게임 Sandrop TIL 6 85 | 소리꽃 KeyBloom TIL 6 86 | 모래게임 Sandrop TIL 7 87 | 모래게임 Sandrop TIL 8 88 | 소리꽃 KeyBloom TIL 7 89 | 모래게임 Sandrop TIL 9 90 | 소리꽃 KeyBloom TIL 8 91 | 모래게임 Sandrop TIL 10 92 | 소리꽃 KeyBloom TIL 9 93 | 콘티온 ContiOn TIL 1 94 | 소리꽃 KeyBloom TIL 10 95 | 콘티온 ContiOn TIL 2 96 | 습관만들기 Pawbit TIL 13 97 | 콘티온 ContiOn TIL 3 98 | 룸톤 Roomtone TIL 1 99 | 모래게임 Sandrop TIL 11 100 | 소리꽃 KeyBloom TIL 11 101 | 여둘까 Office Layout TIL 5 102 | 모래게임 Sandrop TIL 12 103 | 모래게임 Sandrop TIL 13 104 | 콘티온 ContiOn TIL 4 105 | 모래게임 Sandrop TIL 14 106 | 소리꽃 KeyBloom TIL 12 107 | 습관만들기 Pawbit TIL 14 108 | 모래게임 Sandrop TIL 15 109 | 모래게임 Sandrop TIL 16 110 | 소리꽃 KeyBloom TIL 13 111 | 온실 GreenHouse TIL 1 112 | 콘티온 ContiOn TIL 5 113 | 모래게임 Sandrop TIL 17 114 | 소리꽃 KeyBloom TIL 14 115 | 온실 GreenHouse TIL 2 116 | 콘티온 ContiOn TIL 6 117 | 모래게임 Sandrop TIL 18 118 | 콘티온 ContiOn TIL 7 119 | 모래게임 Sandrop TIL 19 120 | 소리꽃 KeyBloom TIL 15 121 | 룸톤 Roomtone TIL 2 122 | 모래게임 Sandrop TIL 20 123 | 모래게임 Sandrop TIL 21 124 | 소리꽃 KeyBloom TIL 16 125 | 소리꽃 KeyBloom TIL 17 126 | 소리꽃 KeyBloom TIL 18 127 | 여둘까 Office Layout TIL 6 128 | 소리꽃 KeyBloom TIL 19 129 | 소리꽃 KeyBloom TIL 20 130 | 콘티온 ContiOn TIL 8 131 | 콘티온 ContiOn TIL 9 132 | 로그스톤 상표 셀프 출원 TIL 1 133 | 소리꽃 KeyBloom TIL 21 134 | 로그스톤 샵 LogStone Shop TIL 1 135 | 소리꽃 KeyBloom TIL 22 136 | 로그스톤 샵 LogStone Shop TIL 2 137 | 룸톤 Roomtone TIL 3 138 | 소리꽃 KeyBloom TIL 23 139 | 모래게임 Sandrop TIL 22 140 | 모래게임 Sandrop TIL 23 141 | 소리꽃 KeyBloom TIL 24 142 | 로그스톤 샵 LogStone Shop TIL 3 143 | 모래게임 Sandrop TIL 24 144 | 소리꽃 KeyBloom TIL 25 145 | 모래게임 Sandrop TIL 25 146 | MiniMacro TIL 1 147 | 룸톤 Roomtone TIL 4 148 | 모래게임 Sandrop TIL 26 149 | 콘티온 ContiOn TIL 10 150 | Astro가 무엇인지, 왜 옮기는지 151 | 룸톤 Roomtone TIL 5 152 | 룸톤 Roomtone TIL 6 153 | 모래게임 Sandrop TIL 27 154 | 소리꽃 KeyBloom TIL 26 155 | MiniMacro TIL 2 156 | 로그스톤 샵 LogStone Shop TIL 4 157 | 메트로놈 Simple Metronome TIL 8 158 | 모래게임 Sandrop TIL 28 159 | 여둘까 Office Layout TIL 7 160 | 룸톤 Roomtone TIL 7 161 | 메트로놈 Simple Metronome TIL 9 162 | 블로그 Astro 이관 TIL 163 | 여둘까 Office Layout TIL 8 164 | 로그스톤 샵 LogStone Shop TIL 5 165 | 모래게임 Sandrop TIL 29 166 | 오픈데이 Openday TIL 1 167 | 로그스톤 샵 LogStone Shop TIL 6 168 | 모래게임 Sandrop TIL 30 169 | 오픈데이 Openday TIL 2 170 | 모래게임 Sandrop TIL 31 171 | Unreal Engine MCP TIL 1 172 | 모래게임 Sandrop TIL 32 173 | 소리꽃 KeyBloom TIL 27 174 | 콘티온 ContiOn TIL 11 175 | 오픈데이 Openday TIL 3 176 | 로그스톤 샵 LogStone Shop TIL 7 177 | 모래게임 Sandrop TIL 33 178 | 소리꽃 KeyBloom TIL 28 179 | 오픈데이 Openday TIL 4 180 | 여둘까 Office Layout TIL 9 181 | 오픈데이 Openday TIL 5 182 | ScorePlayer TIL 1 183 | 모래게임 Sandrop TIL 34 184 | BuildingHub TIL 1 185 | ScorePlayer TIL 2 186 | 여둘까 Office Layout TIL 10 187 | BuildingHub TIL 2 188 | ScorePlayer TIL 3 189 | Unreal Engine MCP TIL 2 190 | 궁 미로 PalaceMaze TIL 1 191 | 메트로놈 Simple Metronome TIL 10 192 | 메트로놈 Simple Metronome TIL 11 193 | 오픈데이 Openday TIL 6 194 | BuildingHub TIL 3 195 | ScorePlayer TIL 4 196 | Obsidian vault에서 코드만 빼기 — directory junction 197 | 여둘까 Office Layout TIL 11 198 | 오픈데이 Openday TIL 7 199 | URL은 바뀔 수 있는 것에 묶지 않는다 200 | 도구는 기능이 아니라 내 일에 맞는지로 고른다 201 | 돌이키기 힘든 변경은 작게 먼저 확인한다 202 | 궁 미로 PalaceMaze TIL 2 203 | 궁 미로 PalaceMaze TIL 3 204 | 소리꽃 KeyBloom TIL 29 205 | 오픈데이 Openday TIL 8 206 | 룸톤 Roomtone TIL 8 207 | BuildingHub TIL 4 208 | ScorePlayer TIL 5 209 | 로그스톤 샵 LogStone Shop TIL 8 210 | 여둘까 Office Layout TIL 12 211 | 오픈데이 Openday TIL 9 212 | BuildingHub TIL 5 213 | MiniMacro TIL 3 214 | 룸톤 Roomtone TIL 10 215 | 룸톤 Roomtone TIL 9 216 | 소리꽃 KeyBloom TIL 30 217 | 오픈데이 Openday TIL 10 218 | 여둘까 Office Layout TIL 13 219 | 룸톤 Roomtone TIL 11 220 | 소리꽃 KeyBloom TIL 31 221 | 궁 미로 PalaceMaze TIL 4 222 | 룸톤 Roomtone TIL 12 223 | 로그스톤 샵 LogStone Shop TIL 9 224 | 룸톤 Roomtone TIL 13 225 | 로그스톤 샵 LogStone Shop TIL 10 226 | 룸톤 Roomtone TIL 14 227 | 소리꽃 KeyBloom TIL 32 228 | 룸톤 Roomtone TIL 15 229 | 룸톤 Roomtone TIL 16 230 | 룸톤 Roomtone TIL 17 231 | 룸톤 Roomtone TIL 18 232 | 메트로놈 Simple Metronome TIL 12 233 | 온실 GreenHouse TIL 3 234 | 룸톤 Roomtone TIL 19 읽는 중 235 | 여러 세션을 INBOX 하나로 굴리기