모래게임 Sandrop TIL 10
이 글은 Today I Learn 시리즈의 66번째 기록입니다. (총 125개)
다 밝히면 아무것도 안 보인다
바닥 밝기로 “지금 나갈 수 있는 길”을 보여 주려고 빈칸을 전부 밝혔다. 그랬더니 오히려 헷갈렸다.
사방이 바스켓으로 둘러싸여 지금은 못 나가는 빈칸까지 같이 밝아서, 어디가 진짜 길인지 흐려졌다. 지나갈 수 있는 빈칸은 그냥 빈칸이 아니라 출구까지 실제로 이어진 빈칸이다.
- 강조는 대상을 좁힐수록 세진다. 조건에 맞는 것을 전부 밝히면 강조가 아니라 배경이 된다
- “이 조건이면 밝힌다”를 정할 때, 그 조건이 사람이 알고 싶은 것과 같은지 확인한다. 비어 있다는 것과 갈 수 있다는 것은 다르다
같은 규칙을 두 번 짜지 않는다
출구까지 이어진 빈칸을 화면 쪽에서 다시 계산할 수도 있었다. 그러면 같은 규칙이 게임 규칙과 화면 두 곳에 생겨 언젠가 어긋난다.
그런데 게임 규칙은 이미 그 계산을 하고 있었다. 바스켓을 꺼낼 수 있는지 판정할 때 쓰는 값이 정확히 그것이다. 규칙을 새로 만들지 않고 그 결과를 읽을 수 있는 창구만 열었다.
이건 규칙을 바꾼 게 아니다. 하는 일은 그대로고 이미 나온 값을 화면이 보게만 한 것이라, 검증 도구 쪽에 똑같이 만들 필요도 없다.
- 화면에 필요한 값이 규칙 안에 이미 있는 경우가 많다. 새로 계산하기 전에 있는지 먼저 찾는다
- 규칙과 표현을 가르는 선이 여기서 쓸모가 있다. 표현 쪽으로 값을 꺼내는 것은 규칙 변경이 아니라서 양쪽을 맞출 대상에서 빠진다
규모를 먼저 본다
화면은 벨트가 돌기 때문에 매 프레임 다시 그려지고, 그때마다 이 계산이 두 번 돈다. 보통 “매 프레임 탐색”은 경보가 울릴 이야기다.
그런데 이 보드는 최대 일곱 칸 곱하기 일곱 칸이다. 마흔아홉 칸을 두 번 훑는 것은 초당 예순 번 해도 티가 안 난다. 그래서 결과를 저장해 두는 장치 없이 매번 계산한다.
- 최적화 판단은 규모를 먼저 보고 한다. 규모가 작으면 안 해도 되는 일이 많고, 안 하면 그만큼 단순해진다
- 저장해 두는 장치는 공짜가 아니다. 언제 무효화할지를 관리해야 하고 그게 새 버그의 자리가 된다
요약
빈칸을 전부 밝힌 것이 실패한 이유는 조건이 사람의 질문과 달랐기 때문이다. 사람은 “여기가 비었나”가 아니라 “여기로 나갈 수 있나”를 묻고 있었다.
그리고 그 답은 이미 게임 규칙이 계산하고 있었다. 새로 만들지 않고 꺼내 보여 주는 것으로 끝났고, 그 편이 두 곳이 어긋날 걱정도 없다.
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 | insertOnConflictUpdate vs DoUpdate(target) 27 | 세션 필터 28 | 아코디언(Accordiaon) UI를 펼친상태로 만들기 29 | input의 step 30 | Word Cloud 31 | Google Sheets를 데이터 버스로(with AppSheet) 32 | Django 모델 텍스트 필드 자동 수집 패턴 33 | localStorage로 섹션 토글 상태 유지 34 | 순차 ID 생성(`select_for_update()` + `max()` 조합) 35 | 역참조 검색과 distinct() 36 | xlsx 다운로드와 로딩 오버레이 충돌 37 | Android 파일 공유 MIME 타입 38 | AssetManifest — Flutter 빌드 타임 asset 목록 런타임 조회 39 | UTF-8 BOM과 PowerShell 파일 쓰기 40 | 소리꽃 KeyBloom TIL 1 41 | 소리꽃 KeyBloom TIL 2 42 | 소리꽃 KeyBloom TIL 3 43 | 메트로놈 Simple Metronome TIL 1 44 | 소리꽃 KeyBloom TIL 4 45 | 메트로놈 Simple Metronome TIL 2 46 | 소리꽃 KeyBloom TIL 5 47 | 메트로놈 Simple Metronome TIL 3 48 | 정적 블로그 SEO 정비와 Pagefind 검색 도입 49 | 메트로놈 Simple Metronome TIL 4 50 | 안드로이드 AudioTrack 연속 재생, 실측 피커 정렬, 카메라 토치 플래시 51 | 메트로놈 Simple Metronome TIL 5 52 | 모래게임 Sandrop TIL 1 53 | 메트로놈 Simple Metronome TIL 6 54 | 모래게임 Sandrop TIL 2 55 | 모래게임 Sandrop TIL 3 56 | 메트로놈 Simple Metronome TIL 7 57 | 모래게임 Sandrop TIL 4 58 | 모래게임 Sandrop TIL 5 59 | 모래게임 Sandrop TIL 6 60 | 소리꽃 KeyBloom TIL 6 61 | 모래게임 Sandrop TIL 7 62 | 모래게임 Sandrop TIL 8 63 | 소리꽃 KeyBloom TIL 7 64 | 모래게임 Sandrop TIL 9 65 | 소리꽃 KeyBloom TIL 8 66 | 모래게임 Sandrop TIL 10 읽는 중 67 | 소리꽃 KeyBloom TIL 9 68 | 소리꽃 KeyBloom TIL 10 69 | 소리꽃 KeyBloom TIL 11 70 | 소리꽃 KeyBloom TIL 12 71 | 소리꽃 KeyBloom TIL 13 72 | 온실 GreenHouse TIL 1 73 | 소리꽃 KeyBloom TIL 14 74 | 온실 GreenHouse TIL 2 75 | 소리꽃 KeyBloom TIL 15 76 | 소리꽃 KeyBloom TIL 16 77 | 소리꽃 KeyBloom TIL 17 78 | 소리꽃 KeyBloom TIL 18 79 | 소리꽃 KeyBloom TIL 19 80 | 소리꽃 KeyBloom TIL 20 81 | 로그스톤 상표 셀프 출원 TIL 1 82 | 소리꽃 KeyBloom TIL 21 83 | 소리꽃 KeyBloom TIL 22 84 | 소리꽃 KeyBloom TIL 23 85 | 소리꽃 KeyBloom TIL 24 86 | MiniMacro TIL 1 87 | Astro가 무엇인지, 왜 옮기는지 88 | MiniMacro TIL 2 89 | 메트로놈 Simple Metronome TIL 8 90 | 메트로놈 Simple Metronome TIL 9 91 | 블로그 Astro 이관 TIL 92 | 오픈데이 Openday TIL 1 93 | 오픈데이 Openday TIL 2 94 | Unreal Engine MCP TIL 1 95 | 콘티온 Conti On TIL 11 96 | 오픈데이 Openday TIL 3 97 | 오픈데이 Openday TIL 4 98 | 오픈데이 Openday TIL 5 99 | ScorePlayer TIL 1 100 | BuildingHub TIL 1 101 | ScorePlayer TIL 2 102 | BuildingHub TIL 2 103 | ScorePlayer TIL 3 104 | Unreal Engine MCP TIL 2 105 | 궁 미로 PalaceMaze TIL 1 106 | 메트로놈 Simple Metronome TIL 10 107 | 메트로놈 Simple Metronome TIL 11 108 | 오픈데이 Openday TIL 6 109 | BuildingHub TIL 3 110 | Obsidian vault에서 코드만 빼기 — directory junction 111 | ScorePlayer TIL 4 112 | 오픈데이 Openday TIL 7 113 | URL은 바뀔 수 있는 것에 묶지 않는다 114 | 도구는 기능이 아니라 내 일에 맞는지로 고른다 115 | 돌이키기 힘든 변경은 작게 먼저 확인한다 116 | 궁 미로 PalaceMaze TIL 3 117 | 궁 미로 PalaceMaze TIL 2 118 | 소리꽃 KeyBloom TIL 29 119 | 오픈데이 Openday TIL 8 120 | BuildingHub TIL 4 121 | ScorePlayer TIL 5 122 | BuildingHub TIL 5 123 | MiniMacro TIL 3 124 | 소리꽃 KeyBloom TIL 30 125 | 궁 미로 PalaceMaze TIL 4