oh-my-oop 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (660) hide show
  1. package/MCP_STRUCTURE.md +301 -0
  2. package/README.md +167 -0
  3. package/SCOPE.md +27 -0
  4. package/dist/application/discovery.d.ts +133 -0
  5. package/dist/application/discovery.js +62 -0
  6. package/dist/application/discovery.js.map +1 -0
  7. package/dist/cli.d.ts +2 -0
  8. package/dist/cli.js +80 -0
  9. package/dist/cli.js.map +1 -0
  10. package/dist/config.d.ts +16 -0
  11. package/dist/config.js +32 -0
  12. package/dist/config.js.map +1 -0
  13. package/dist/domain/collaborators.d.ts +2 -0
  14. package/dist/domain/collaborators.js +26 -0
  15. package/dist/domain/collaborators.js.map +1 -0
  16. package/dist/domain/ids.d.ts +4 -0
  17. package/dist/domain/ids.js +23 -0
  18. package/dist/domain/ids.js.map +1 -0
  19. package/dist/domain/model.d.ts +71 -0
  20. package/dist/domain/model.js +2 -0
  21. package/dist/domain/model.js.map +1 -0
  22. package/dist/domain/schemas.d.ts +213 -0
  23. package/dist/domain/schemas.js +79 -0
  24. package/dist/domain/schemas.js.map +1 -0
  25. package/dist/domain/stereotypes.d.ts +7 -0
  26. package/dist/domain/stereotypes.js +65 -0
  27. package/dist/domain/stereotypes.js.map +1 -0
  28. package/dist/index.d.ts +2 -0
  29. package/dist/index.js +21 -0
  30. package/dist/index.js.map +1 -0
  31. package/dist/io/classStore.d.ts +9 -0
  32. package/dist/io/classStore.js +39 -0
  33. package/dist/io/classStore.js.map +1 -0
  34. package/dist/io/collaborationStore.d.ts +7 -0
  35. package/dist/io/collaborationStore.js +32 -0
  36. package/dist/io/collaborationStore.js.map +1 -0
  37. package/dist/io/design.d.ts +3 -0
  38. package/dist/io/design.js +22 -0
  39. package/dist/io/design.js.map +1 -0
  40. package/dist/io/designIndex.d.ts +6 -0
  41. package/dist/io/designIndex.js +49 -0
  42. package/dist/io/designIndex.js.map +1 -0
  43. package/dist/io/frontmatter.d.ts +8 -0
  44. package/dist/io/frontmatter.js +31 -0
  45. package/dist/io/frontmatter.js.map +1 -0
  46. package/dist/io/history.d.ts +10 -0
  47. package/dist/io/history.js +38 -0
  48. package/dist/io/history.js.map +1 -0
  49. package/dist/io/useCaseStore.d.ts +8 -0
  50. package/dist/io/useCaseStore.js +36 -0
  51. package/dist/io/useCaseStore.js.map +1 -0
  52. package/dist/io/workspace.d.ts +14 -0
  53. package/dist/io/workspace.js +82 -0
  54. package/dist/io/workspace.js.map +1 -0
  55. package/dist/oop/commands.d.ts +446 -0
  56. package/dist/oop/commands.js +319 -0
  57. package/dist/oop/commands.js.map +1 -0
  58. package/dist/oop/conformance.d.ts +16 -0
  59. package/dist/oop/conformance.js +30 -0
  60. package/dist/oop/conformance.js.map +1 -0
  61. package/dist/prompts/discovery.d.ts +2 -0
  62. package/dist/prompts/discovery.js +41 -0
  63. package/dist/prompts/discovery.js.map +1 -0
  64. package/dist/prompts/imagineWithoutController.d.ts +2 -0
  65. package/dist/prompts/imagineWithoutController.js +75 -0
  66. package/dist/prompts/imagineWithoutController.js.map +1 -0
  67. package/dist/prompts/index.d.ts +2 -0
  68. package/dist/prompts/index.js +17 -0
  69. package/dist/prompts/index.js.map +1 -0
  70. package/dist/prompts/phasePressureTest.d.ts +2 -0
  71. package/dist/prompts/phasePressureTest.js +69 -0
  72. package/dist/prompts/phasePressureTest.js.map +1 -0
  73. package/dist/prompts/rddIntro.d.ts +2 -0
  74. package/dist/prompts/rddIntro.js +53 -0
  75. package/dist/prompts/rddIntro.js.map +1 -0
  76. package/dist/prompts/review.d.ts +2 -0
  77. package/dist/prompts/review.js +45 -0
  78. package/dist/prompts/review.js.map +1 -0
  79. package/dist/prompts/stateMachineIntrospect.d.ts +2 -0
  80. package/dist/prompts/stateMachineIntrospect.js +80 -0
  81. package/dist/prompts/stateMachineIntrospect.js.map +1 -0
  82. package/dist/prompts/tellDontAskRephrase.d.ts +2 -0
  83. package/dist/prompts/tellDontAskRephrase.js +66 -0
  84. package/dist/prompts/tellDontAskRephrase.js.map +1 -0
  85. package/dist/render/diff.d.ts +21 -0
  86. package/dist/render/diff.js +84 -0
  87. package/dist/render/diff.js.map +1 -0
  88. package/dist/render/mermaid.d.ts +24 -0
  89. package/dist/render/mermaid.js +53 -0
  90. package/dist/render/mermaid.js.map +1 -0
  91. package/dist/render/sideBySide.d.ts +14 -0
  92. package/dist/render/sideBySide.js +91 -0
  93. package/dist/render/sideBySide.js.map +1 -0
  94. package/dist/resources/index.d.ts +2 -0
  95. package/dist/resources/index.js +349 -0
  96. package/dist/resources/index.js.map +1 -0
  97. package/dist/server.d.ts +2 -0
  98. package/dist/server.js +22 -0
  99. package/dist/server.js.map +1 -0
  100. package/dist/tools/alternatives.d.ts +2 -0
  101. package/dist/tools/alternatives.js +9 -0
  102. package/dist/tools/alternatives.js.map +1 -0
  103. package/dist/tools/classes.d.ts +2 -0
  104. package/dist/tools/classes.js +13 -0
  105. package/dist/tools/classes.js.map +1 -0
  106. package/dist/tools/collaborations.d.ts +2 -0
  107. package/dist/tools/collaborations.js +8 -0
  108. package/dist/tools/collaborations.js.map +1 -0
  109. package/dist/tools/compare.d.ts +2 -0
  110. package/dist/tools/compare.js +9 -0
  111. package/dist/tools/compare.js.map +1 -0
  112. package/dist/tools/conformance.d.ts +3 -0
  113. package/dist/tools/conformance.js +11 -0
  114. package/dist/tools/conformance.js.map +1 -0
  115. package/dist/tools/diagram.d.ts +2 -0
  116. package/dist/tools/diagram.js +9 -0
  117. package/dist/tools/diagram.js.map +1 -0
  118. package/dist/tools/discovery.d.ts +2 -0
  119. package/dist/tools/discovery.js +23 -0
  120. package/dist/tools/discovery.js.map +1 -0
  121. package/dist/tools/index.d.ts +2 -0
  122. package/dist/tools/index.js +27 -0
  123. package/dist/tools/index.js.map +1 -0
  124. package/dist/tools/init.d.ts +2 -0
  125. package/dist/tools/init.js +9 -0
  126. package/dist/tools/init.js.map +1 -0
  127. package/dist/tools/oop.d.ts +9 -0
  128. package/dist/tools/oop.js +26 -0
  129. package/dist/tools/oop.js.map +1 -0
  130. package/dist/tools/responsibilities.d.ts +2 -0
  131. package/dist/tools/responsibilities.js +13 -0
  132. package/dist/tools/responsibilities.js.map +1 -0
  133. package/dist/tools/state.d.ts +2 -0
  134. package/dist/tools/state.js +8 -0
  135. package/dist/tools/state.js.map +1 -0
  136. package/dist/tools/useCases.d.ts +2 -0
  137. package/dist/tools/useCases.js +18 -0
  138. package/dist/tools/useCases.js.map +1 -0
  139. package/dist/tools/validate.d.ts +2 -0
  140. package/dist/tools/validate.js +9 -0
  141. package/dist/tools/validate.js.map +1 -0
  142. package/dist/tradeoff/engine.d.ts +61 -0
  143. package/dist/tradeoff/engine.js +171 -0
  144. package/dist/tradeoff/engine.js.map +1 -0
  145. package/dist/tradeoff/heuristics/classSplit.d.ts +3 -0
  146. package/dist/tradeoff/heuristics/classSplit.js +94 -0
  147. package/dist/tradeoff/heuristics/classSplit.js.map +1 -0
  148. package/dist/tradeoff/heuristics/collaborationShape.d.ts +2 -0
  149. package/dist/tradeoff/heuristics/collaborationShape.js +82 -0
  150. package/dist/tradeoff/heuristics/collaborationShape.js.map +1 -0
  151. package/dist/tradeoff/heuristics/collectionShape.d.ts +2 -0
  152. package/dist/tradeoff/heuristics/collectionShape.js +113 -0
  153. package/dist/tradeoff/heuristics/collectionShape.js.map +1 -0
  154. package/dist/tradeoff/heuristics/dualSubjectComparison.d.ts +2 -0
  155. package/dist/tradeoff/heuristics/dualSubjectComparison.js +114 -0
  156. package/dist/tradeoff/heuristics/dualSubjectComparison.js.map +1 -0
  157. package/dist/tradeoff/heuristics/errorHandling.d.ts +2 -0
  158. package/dist/tradeoff/heuristics/errorHandling.js +110 -0
  159. package/dist/tradeoff/heuristics/errorHandling.js.map +1 -0
  160. package/dist/tradeoff/heuristics/responsibilitySplit.d.ts +23 -0
  161. package/dist/tradeoff/heuristics/responsibilitySplit.js +183 -0
  162. package/dist/tradeoff/heuristics/responsibilitySplit.js.map +1 -0
  163. package/dist/tradeoff/heuristics/stereotypeChoice.d.ts +2 -0
  164. package/dist/tradeoff/heuristics/stereotypeChoice.js +23 -0
  165. package/dist/tradeoff/heuristics/stereotypeChoice.js.map +1 -0
  166. package/dist/tradeoff/heuristics/strategyOrPolicy.d.ts +2 -0
  167. package/dist/tradeoff/heuristics/strategyOrPolicy.js +110 -0
  168. package/dist/tradeoff/heuristics/strategyOrPolicy.js.map +1 -0
  169. package/dist/tradeoff/heuristics/valueObjectShape.d.ts +2 -0
  170. package/dist/tradeoff/heuristics/valueObjectShape.js +111 -0
  171. package/dist/tradeoff/heuristics/valueObjectShape.js.map +1 -0
  172. package/dist/tradeoff/templates.d.ts +2 -0
  173. package/dist/tradeoff/templates.js +33 -0
  174. package/dist/tradeoff/templates.js.map +1 -0
  175. package/dist/util/log.d.ts +1 -0
  176. package/dist/util/log.js +7 -0
  177. package/dist/util/log.js.map +1 -0
  178. package/dist/util/mcp.d.ts +4 -0
  179. package/dist/util/mcp.js +18 -0
  180. package/dist/util/mcp.js.map +1 -0
  181. package/dist/validate/cohesion.d.ts +3 -0
  182. package/dist/validate/cohesion.js +88 -0
  183. package/dist/validate/cohesion.js.map +1 -0
  184. package/dist/validate/collectionWrapper.d.ts +3 -0
  185. package/dist/validate/collectionWrapper.js +131 -0
  186. package/dist/validate/collectionWrapper.js.map +1 -0
  187. package/dist/validate/coupling.d.ts +3 -0
  188. package/dist/validate/coupling.js +47 -0
  189. package/dist/validate/coupling.js.map +1 -0
  190. package/dist/validate/cycle.d.ts +3 -0
  191. package/dist/validate/cycle.js +101 -0
  192. package/dist/validate/cycle.js.map +1 -0
  193. package/dist/validate/dataDuplication.d.ts +3 -0
  194. package/dist/validate/dataDuplication.js +150 -0
  195. package/dist/validate/dataDuplication.js.map +1 -0
  196. package/dist/validate/dependencyDirection.d.ts +3 -0
  197. package/dist/validate/dependencyDirection.js +106 -0
  198. package/dist/validate/dependencyDirection.js.map +1 -0
  199. package/dist/validate/dualUseKnowing.d.ts +3 -0
  200. package/dist/validate/dualUseKnowing.js +137 -0
  201. package/dist/validate/dualUseKnowing.js.map +1 -0
  202. package/dist/validate/emptyObjectFill.d.ts +3 -0
  203. package/dist/validate/emptyObjectFill.js +119 -0
  204. package/dist/validate/emptyObjectFill.js.map +1 -0
  205. package/dist/validate/findings.d.ts +22 -0
  206. package/dist/validate/findings.js +12 -0
  207. package/dist/validate/findings.js.map +1 -0
  208. package/dist/validate/functionDecompositionExcess.d.ts +3 -0
  209. package/dist/validate/functionDecompositionExcess.js +120 -0
  210. package/dist/validate/functionDecompositionExcess.js.map +1 -0
  211. package/dist/validate/functionNotObject.d.ts +3 -0
  212. package/dist/validate/functionNotObject.js +80 -0
  213. package/dist/validate/functionNotObject.js.map +1 -0
  214. package/dist/validate/godObject.d.ts +6 -0
  215. package/dist/validate/godObject.js +76 -0
  216. package/dist/validate/godObject.js.map +1 -0
  217. package/dist/validate/presentationInDomain.d.ts +3 -0
  218. package/dist/validate/presentationInDomain.js +57 -0
  219. package/dist/validate/presentationInDomain.js.map +1 -0
  220. package/dist/validate/primitiveWrapper.d.ts +3 -0
  221. package/dist/validate/primitiveWrapper.js +106 -0
  222. package/dist/validate/primitiveWrapper.js.map +1 -0
  223. package/dist/validate/rules.d.ts +24 -0
  224. package/dist/validate/rules.js +269 -0
  225. package/dist/validate/rules.js.map +1 -0
  226. package/dist/validate/singletonStatefulHolder.d.ts +3 -0
  227. package/dist/validate/singletonStatefulHolder.js +128 -0
  228. package/dist/validate/singletonStatefulHolder.js.map +1 -0
  229. package/dist/validate/strategyAsymmetry.d.ts +3 -0
  230. package/dist/validate/strategyAsymmetry.js +131 -0
  231. package/dist/validate/strategyAsymmetry.js.map +1 -0
  232. package/dist/validate/testability.d.ts +5 -0
  233. package/dist/validate/testability.js +157 -0
  234. package/dist/validate/testability.js.map +1 -0
  235. package/dist/validate/vagueName.d.ts +3 -0
  236. package/dist/validate/vagueName.js +136 -0
  237. package/dist/validate/vagueName.js.map +1 -0
  238. package/dist/validate/validationLocation.d.ts +3 -0
  239. package/dist/validate/validationLocation.js +120 -0
  240. package/dist/validate/validationLocation.js.map +1 -0
  241. package/lessons/STYLE_GUIDE.md +304 -0
  242. package/lessons/woowacourse-kotlin-blackjack/2chang5/33-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +293 -0
  243. package/lessons/woowacourse-kotlin-blackjack/Choisehyeon/52-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +106 -0
  244. package/lessons/woowacourse-kotlin-blackjack/Choisehyeon/9-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +282 -0
  245. package/lessons/woowacourse-kotlin-blackjack/DYGames/14-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +182 -0
  246. package/lessons/woowacourse-kotlin-blackjack/DYGames/37-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +122 -0
  247. package/lessons/woowacourse-kotlin-blackjack/EmilyCh0/12-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +117 -0
  248. package/lessons/woowacourse-kotlin-blackjack/EmilyCh0/38-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +291 -0
  249. package/lessons/woowacourse-kotlin-blackjack/HANDOVER.md +1475 -0
  250. package/lessons/woowacourse-kotlin-blackjack/HamBeomJoon/119-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +251 -0
  251. package/lessons/woowacourse-kotlin-blackjack/HamBeomJoon/137-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +459 -0
  252. package/lessons/woowacourse-kotlin-blackjack/Hevton/100-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +282 -0
  253. package/lessons/woowacourse-kotlin-blackjack/Hevton/82-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +303 -0
  254. package/lessons/woowacourse-kotlin-blackjack/Hogu59/71-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +134 -0
  255. package/lessons/woowacourse-kotlin-blackjack/Hogu59/96-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +323 -0
  256. package/lessons/woowacourse-kotlin-blackjack/JoYehyun99/66-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +210 -0
  257. package/lessons/woowacourse-kotlin-blackjack/Junyoung-WON/101-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +191 -0
  258. package/lessons/woowacourse-kotlin-blackjack/Junyoung-WON/80-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +253 -0
  259. package/lessons/woowacourse-kotlin-blackjack/Leeyerin0210/108-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +516 -0
  260. package/lessons/woowacourse-kotlin-blackjack/Leeyerin0210/133-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +541 -0
  261. package/lessons/woowacourse-kotlin-blackjack/RightHennessy/22-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +278 -0
  262. package/lessons/woowacourse-kotlin-blackjack/RightHennessy/48-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +188 -0
  263. package/lessons/woowacourse-kotlin-blackjack/SeongHoonC/16-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +228 -0
  264. package/lessons/woowacourse-kotlin-blackjack/SeongHoonC/54-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +227 -0
  265. package/lessons/woowacourse-kotlin-blackjack/Yunseok-Nam/76-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +279 -0
  266. package/lessons/woowacourse-kotlin-blackjack/Yunseok-Nam/86-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +203 -0
  267. package/lessons/woowacourse-kotlin-blackjack/aprilgom/105-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +162 -0
  268. package/lessons/woowacourse-kotlin-blackjack/aprilgom/64-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +279 -0
  269. package/lessons/woowacourse-kotlin-blackjack/boogi-woogi/18-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +188 -0
  270. package/lessons/woowacourse-kotlin-blackjack/boogi-woogi/36-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +769 -0
  271. package/lessons/woowacourse-kotlin-blackjack/briandr97/19-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +226 -0
  272. package/lessons/woowacourse-kotlin-blackjack/briandr97/59-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +193 -0
  273. package/lessons/woowacourse-kotlin-blackjack/chaehyuns/70-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +175 -0
  274. package/lessons/woowacourse-kotlin-blackjack/chaehyuns/98-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +206 -0
  275. package/lessons/woowacourse-kotlin-blackjack/chanho0908/123-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +277 -0
  276. package/lessons/woowacourse-kotlin-blackjack/chanho0908/150-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +219 -0
  277. package/lessons/woowacourse-kotlin-blackjack/chws0508/26-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +259 -0
  278. package/lessons/woowacourse-kotlin-blackjack/chws0508/43-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +189 -0
  279. package/lessons/woowacourse-kotlin-blackjack/cucumber99/109-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +351 -0
  280. package/lessons/woowacourse-kotlin-blackjack/cucumber99/149-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +147 -0
  281. package/lessons/woowacourse-kotlin-blackjack/devfeijoa/121-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +168 -0
  282. package/lessons/woowacourse-kotlin-blackjack/devfeijoa/153-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +116 -0
  283. package/lessons/woowacourse-kotlin-blackjack/doabletuple/126-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +680 -0
  284. package/lessons/woowacourse-kotlin-blackjack/doabletuple/142-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +739 -0
  285. package/lessons/woowacourse-kotlin-blackjack/donghyun81/116-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +297 -0
  286. package/lessons/woowacourse-kotlin-blackjack/donghyun81/147-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +244 -0
  287. package/lessons/woowacourse-kotlin-blackjack/dpcks0509/78-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +232 -0
  288. package/lessons/woowacourse-kotlin-blackjack/dpcks0509/88-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +137 -0
  289. package/lessons/woowacourse-kotlin-blackjack/etama123/112-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +269 -0
  290. package/lessons/woowacourse-kotlin-blackjack/etama123/148-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +240 -0
  291. package/lessons/woowacourse-kotlin-blackjack/gaeun5744/102-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +146 -0
  292. package/lessons/woowacourse-kotlin-blackjack/gaeun5744/69-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +224 -0
  293. package/lessons/woowacourse-kotlin-blackjack/gahyunkim/118-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +397 -0
  294. package/lessons/woowacourse-kotlin-blackjack/gahyunkim/141-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +215 -0
  295. package/lessons/woowacourse-kotlin-blackjack/giovannijunseokim/106-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +395 -0
  296. package/lessons/woowacourse-kotlin-blackjack/giovannijunseokim/134-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +219 -0
  297. package/lessons/woowacourse-kotlin-blackjack/haeum808/62-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +230 -0
  298. package/lessons/woowacourse-kotlin-blackjack/haeum808/89-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +169 -0
  299. package/lessons/woowacourse-kotlin-blackjack/hwannow/110-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +221 -0
  300. package/lessons/woowacourse-kotlin-blackjack/hwannow/132-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +573 -0
  301. package/lessons/woowacourse-kotlin-blackjack/hxeyexn/103-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +188 -0
  302. package/lessons/woowacourse-kotlin-blackjack/hxeyexn/81-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +301 -0
  303. package/lessons/woowacourse-kotlin-blackjack/hyemdooly/21-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +613 -0
  304. package/lessons/woowacourse-kotlin-blackjack/hyemdooly/35-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +691 -0
  305. package/lessons/woowacourse-kotlin-blackjack/hyunji1203/13-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +206 -0
  306. package/lessons/woowacourse-kotlin-blackjack/ii2001/79-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +153 -0
  307. package/lessons/woowacourse-kotlin-blackjack/ii2001/85-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +318 -0
  308. package/lessons/woowacourse-kotlin-blackjack/ijh1298/128-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +250 -0
  309. package/lessons/woowacourse-kotlin-blackjack/ijh1298/135-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +269 -0
  310. package/lessons/woowacourse-kotlin-blackjack/inseonyun/28-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +346 -0
  311. package/lessons/woowacourse-kotlin-blackjack/inseonyun/49-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +360 -0
  312. package/lessons/woowacourse-kotlin-blackjack/ippnsj/30-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +152 -0
  313. package/lessons/woowacourse-kotlin-blackjack/ippnsj/42-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +213 -0
  314. package/lessons/woowacourse-kotlin-blackjack/jaeyeongjo/73-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +247 -0
  315. package/lessons/woowacourse-kotlin-blackjack/jaeyeongjo/87-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +900 -0
  316. package/lessons/woowacourse-kotlin-blackjack/jerry8282/125-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +248 -0
  317. package/lessons/woowacourse-kotlin-blackjack/jerry8282/151-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +243 -0
  318. package/lessons/woowacourse-kotlin-blackjack/jinuemong/63-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +281 -0
  319. package/lessons/woowacourse-kotlin-blackjack/jinuemong/92-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +283 -0
  320. package/lessons/woowacourse-kotlin-blackjack/jiyuneel/113-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +348 -0
  321. package/lessons/woowacourse-kotlin-blackjack/jiyuneel/140-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +265 -0
  322. package/lessons/woowacourse-kotlin-blackjack/junjange/61-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +270 -0
  323. package/lessons/woowacourse-kotlin-blackjack/junjange/93-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +465 -0
  324. package/lessons/woowacourse-kotlin-blackjack/junseo511/107-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +296 -0
  325. package/lessons/woowacourse-kotlin-blackjack/junseo511/145-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +316 -0
  326. package/lessons/woowacourse-kotlin-blackjack/ki960213/11-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +175 -0
  327. package/lessons/woowacourse-kotlin-blackjack/kimhm0728/72-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +458 -0
  328. package/lessons/woowacourse-kotlin-blackjack/kimhm0728/97-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +225 -0
  329. package/lessons/woowacourse-kotlin-blackjack/kkosang/68-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +221 -0
  330. package/lessons/woowacourse-kotlin-blackjack/kkosang/94-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +158 -0
  331. package/lessons/woowacourse-kotlin-blackjack/kmkim2689/65-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +252 -0
  332. package/lessons/woowacourse-kotlin-blackjack/kmkim2689/90-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +460 -0
  333. package/lessons/woowacourse-kotlin-blackjack/krrong/32-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +216 -0
  334. package/lessons/woowacourse-kotlin-blackjack/krrong/46-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +285 -0
  335. package/lessons/woowacourse-kotlin-blackjack/m6z1/122-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +177 -0
  336. package/lessons/woowacourse-kotlin-blackjack/m6z1/144-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +155 -0
  337. package/lessons/woowacourse-kotlin-blackjack/medAndro/130-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +683 -0
  338. package/lessons/woowacourse-kotlin-blackjack/medAndro/143-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +678 -0
  339. package/lessons/woowacourse-kotlin-blackjack/moondev03/114-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +262 -0
  340. package/lessons/woowacourse-kotlin-blackjack/moondev03/131-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +498 -0
  341. package/lessons/woowacourse-kotlin-blackjack/murjune/77-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +287 -0
  342. package/lessons/woowacourse-kotlin-blackjack/murjune/91-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +280 -0
  343. package/lessons/woowacourse-kotlin-blackjack/no1msh/31-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +250 -0
  344. package/lessons/woowacourse-kotlin-blackjack/otter66/24-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +302 -0
  345. package/lessons/woowacourse-kotlin-blackjack/otter66/58-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +391 -0
  346. package/lessons/woowacourse-kotlin-blackjack/oungsi2000/111-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +253 -0
  347. package/lessons/woowacourse-kotlin-blackjack/oungsi2000/136-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +540 -0
  348. package/lessons/woowacourse-kotlin-blackjack/parkjiminnnn/117-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +819 -0
  349. package/lessons/woowacourse-kotlin-blackjack/parkjiminnnn/139-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +683 -0
  350. package/lessons/woowacourse-kotlin-blackjack/pingu244/20-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +258 -0
  351. package/lessons/woowacourse-kotlin-blackjack/pingu244/41-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +171 -0
  352. package/lessons/woowacourse-kotlin-blackjack/re4rk/34-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +289 -0
  353. package/lessons/woowacourse-kotlin-blackjack/re4rk/8-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +297 -0
  354. package/lessons/woowacourse-kotlin-blackjack/rhkrwngud445/17-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +279 -0
  355. package/lessons/woowacourse-kotlin-blackjack/rhkrwngud445/50-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +145 -0
  356. package/lessons/woowacourse-kotlin-blackjack/rhthrhrl0/23-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +253 -0
  357. package/lessons/woowacourse-kotlin-blackjack/rhthrhrl0/39-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +238 -0
  358. package/lessons/woowacourse-kotlin-blackjack/rosemin928/129-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +726 -0
  359. package/lessons/woowacourse-kotlin-blackjack/rosemin928/138-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +845 -0
  360. package/lessons/woowacourse-kotlin-blackjack/s6m1n/67-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +220 -0
  361. package/lessons/woowacourse-kotlin-blackjack/s6m1n/99-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +229 -0
  362. package/lessons/woowacourse-kotlin-blackjack/s9hn/10-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +284 -0
  363. package/lessons/woowacourse-kotlin-blackjack/sh1mj1/75-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +224 -0
  364. package/lessons/woowacourse-kotlin-blackjack/songpink/74-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +238 -0
  365. package/lessons/woowacourse-kotlin-blackjack/songpink/95-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +216 -0
  366. package/lessons/woowacourse-kotlin-blackjack/sujin9/15-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +132 -0
  367. package/lessons/woowacourse-kotlin-blackjack/sujin9/47-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +265 -0
  368. package/lessons/woowacourse-kotlin-blackjack/tmdgh1592/29-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +305 -0
  369. package/lessons/woowacourse-kotlin-blackjack/tmdgh1592/51-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +278 -0
  370. package/lessons/woowacourse-kotlin-blackjack/tobae-time/115-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +305 -0
  371. package/lessons/woowacourse-kotlin-blackjack/tobae-time/154-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +298 -0
  372. package/lessons/woowacourse-kotlin-blackjack/whk06061/25-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +235 -0
  373. package/lessons/woowacourse-kotlin-blackjack/whk06061/53-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +130 -0
  374. package/lessons/woowacourse-kotlin-blackjack/wondroid-world/124-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +486 -0
  375. package/lessons/woowacourse-kotlin-blackjack/wondroid-world/152-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +482 -0
  376. package/lessons/woowacourse-kotlin-blackjack/yrsel/120-1/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +194 -0
  377. package/lessons/woowacourse-kotlin-blackjack/yrsel/146-2/353/213/250/352/263/204-/353/270/224/353/236/231/354/236/255.md +444 -0
  378. package/lessons/woowacourse-kotlin-lotto/2chang5/27-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +155 -0
  379. package/lessons/woowacourse-kotlin-lotto/2chang5/52-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +187 -0
  380. package/lessons/woowacourse-kotlin-lotto/Choisehyeon/14-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +206 -0
  381. package/lessons/woowacourse-kotlin-lotto/Choisehyeon/47-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +119 -0
  382. package/lessons/woowacourse-kotlin-lotto/DYGames/2-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +83 -0
  383. package/lessons/woowacourse-kotlin-lotto/DYGames/34-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +88 -0
  384. package/lessons/woowacourse-kotlin-lotto/EmilyCh0/12-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +107 -0
  385. package/lessons/woowacourse-kotlin-lotto/EmilyCh0/40-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +135 -0
  386. package/lessons/woowacourse-kotlin-lotto/HANDOVER.md +217 -0
  387. package/lessons/woowacourse-kotlin-lotto/HamBeomJoon/121-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +66 -0
  388. package/lessons/woowacourse-kotlin-lotto/HamBeomJoon/139-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +75 -0
  389. package/lessons/woowacourse-kotlin-lotto/Hevton/76-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +21 -0
  390. package/lessons/woowacourse-kotlin-lotto/Hevton/92-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +122 -0
  391. package/lessons/woowacourse-kotlin-lotto/Hogu59/100-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +110 -0
  392. package/lessons/woowacourse-kotlin-lotto/Hogu59/68-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +84 -0
  393. package/lessons/woowacourse-kotlin-lotto/JoYehyun99/60-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +176 -0
  394. package/lessons/woowacourse-kotlin-lotto/JoYehyun99/96-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +71 -0
  395. package/lessons/woowacourse-kotlin-lotto/Junyoung-WON/61-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +143 -0
  396. package/lessons/woowacourse-kotlin-lotto/Junyoung-WON/93-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +16 -0
  397. package/lessons/woowacourse-kotlin-lotto/Leeyerin0210/109-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +57 -0
  398. package/lessons/woowacourse-kotlin-lotto/Leeyerin0210/135-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +115 -0
  399. package/lessons/woowacourse-kotlin-lotto/PROGRESS.md +160 -0
  400. package/lessons/woowacourse-kotlin-lotto/README.md +77 -0
  401. package/lessons/woowacourse-kotlin-lotto/RightHennessy/32-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +178 -0
  402. package/lessons/woowacourse-kotlin-lotto/RightHennessy/5-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +149 -0
  403. package/lessons/woowacourse-kotlin-lotto/SUMMARY.md +369 -0
  404. package/lessons/woowacourse-kotlin-lotto/SeongHoonC/25-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +129 -0
  405. package/lessons/woowacourse-kotlin-lotto/SeongHoonC/37-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +27 -0
  406. package/lessons/woowacourse-kotlin-lotto/Yunseok-Nam/72-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +137 -0
  407. package/lessons/woowacourse-kotlin-lotto/Yunseok-Nam/86-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +17 -0
  408. package/lessons/woowacourse-kotlin-lotto/aprilgom/102-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +62 -0
  409. package/lessons/woowacourse-kotlin-lotto/aprilgom/64-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +146 -0
  410. package/lessons/woowacourse-kotlin-lotto/boogi-woogi/11-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +26 -0
  411. package/lessons/woowacourse-kotlin-lotto/boogi-woogi/29-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +26 -0
  412. package/lessons/woowacourse-kotlin-lotto/briandr97/26-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +52 -0
  413. package/lessons/woowacourse-kotlin-lotto/briandr97/51-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +123 -0
  414. package/lessons/woowacourse-kotlin-lotto/chaehyuns/71-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +115 -0
  415. package/lessons/woowacourse-kotlin-lotto/chaehyuns/97-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +107 -0
  416. package/lessons/woowacourse-kotlin-lotto/chanho0908/124-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +51 -0
  417. package/lessons/woowacourse-kotlin-lotto/chanho0908/129-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +149 -0
  418. package/lessons/woowacourse-kotlin-lotto/chws0508/24-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +117 -0
  419. package/lessons/woowacourse-kotlin-lotto/chws0508/50-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +167 -0
  420. package/lessons/woowacourse-kotlin-lotto/cucumber99/116-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +155 -0
  421. package/lessons/woowacourse-kotlin-lotto/cucumber99/147-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +223 -0
  422. package/lessons/woowacourse-kotlin-lotto/devfeijoa/125-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +68 -0
  423. package/lessons/woowacourse-kotlin-lotto/devfeijoa/153-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +107 -0
  424. package/lessons/woowacourse-kotlin-lotto/doabletuple/119-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +157 -0
  425. package/lessons/woowacourse-kotlin-lotto/doabletuple/138-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +77 -0
  426. package/lessons/woowacourse-kotlin-lotto/donghyun81/111-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +67 -0
  427. package/lessons/woowacourse-kotlin-lotto/donghyun81/152-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +124 -0
  428. package/lessons/woowacourse-kotlin-lotto/dpcks0509/80-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +141 -0
  429. package/lessons/woowacourse-kotlin-lotto/dpcks0509/87-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +134 -0
  430. package/lessons/woowacourse-kotlin-lotto/etama123/112-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +170 -0
  431. package/lessons/woowacourse-kotlin-lotto/etama123/148-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +183 -0
  432. package/lessons/woowacourse-kotlin-lotto/gaeun5744/101-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +21 -0
  433. package/lessons/woowacourse-kotlin-lotto/gaeun5744/78-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +158 -0
  434. package/lessons/woowacourse-kotlin-lotto/gahyunkim/107-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +83 -0
  435. package/lessons/woowacourse-kotlin-lotto/gahyunkim/136-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +51 -0
  436. package/lessons/woowacourse-kotlin-lotto/giovannijunseokim/106-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +171 -0
  437. package/lessons/woowacourse-kotlin-lotto/giovannijunseokim/137-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +111 -0
  438. package/lessons/woowacourse-kotlin-lotto/haeum808/67-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +52 -0
  439. package/lessons/woowacourse-kotlin-lotto/haeum808/95-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +97 -0
  440. package/lessons/woowacourse-kotlin-lotto/hwannow/113-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +235 -0
  441. package/lessons/woowacourse-kotlin-lotto/hwannow/132-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +149 -0
  442. package/lessons/woowacourse-kotlin-lotto/hxeyexn/77-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +141 -0
  443. package/lessons/woowacourse-kotlin-lotto/hxeyexn/98-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +162 -0
  444. package/lessons/woowacourse-kotlin-lotto/hyemdooly/17-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +19 -0
  445. package/lessons/woowacourse-kotlin-lotto/hyemdooly/28-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +23 -0
  446. package/lessons/woowacourse-kotlin-lotto/hyunji1203/15-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +171 -0
  447. package/lessons/woowacourse-kotlin-lotto/hyunji1203/48-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +150 -0
  448. package/lessons/woowacourse-kotlin-lotto/ii2001/62-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +104 -0
  449. package/lessons/woowacourse-kotlin-lotto/ii2001/88-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +20 -0
  450. package/lessons/woowacourse-kotlin-lotto/ijh1298/122-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +179 -0
  451. package/lessons/woowacourse-kotlin-lotto/ijh1298/133-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +153 -0
  452. package/lessons/woowacourse-kotlin-lotto/inseonyun/3-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +222 -0
  453. package/lessons/woowacourse-kotlin-lotto/inseonyun/49-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +166 -0
  454. package/lessons/woowacourse-kotlin-lotto/ippnsj/16-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +154 -0
  455. package/lessons/woowacourse-kotlin-lotto/ippnsj/55-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +145 -0
  456. package/lessons/woowacourse-kotlin-lotto/jaeyeongjo/59-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +68 -0
  457. package/lessons/woowacourse-kotlin-lotto/jaeyeongjo/83-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +53 -0
  458. package/lessons/woowacourse-kotlin-lotto/jerry8282/115-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +97 -0
  459. package/lessons/woowacourse-kotlin-lotto/jerry8282/134-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +145 -0
  460. package/lessons/woowacourse-kotlin-lotto/jinuemong/63-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +144 -0
  461. package/lessons/woowacourse-kotlin-lotto/jinuemong/89-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +148 -0
  462. package/lessons/woowacourse-kotlin-lotto/jiyuneel/128-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +52 -0
  463. package/lessons/woowacourse-kotlin-lotto/jiyuneel/144-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +149 -0
  464. package/lessons/woowacourse-kotlin-lotto/junjange/58-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +148 -0
  465. package/lessons/woowacourse-kotlin-lotto/junjange/81-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +178 -0
  466. package/lessons/woowacourse-kotlin-lotto/junseo511/120-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +153 -0
  467. package/lessons/woowacourse-kotlin-lotto/junseo511/131-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +188 -0
  468. package/lessons/woowacourse-kotlin-lotto/ki960213/43-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +24 -0
  469. package/lessons/woowacourse-kotlin-lotto/ki960213/8-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +159 -0
  470. package/lessons/woowacourse-kotlin-lotto/kimhm0728/74-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +50 -0
  471. package/lessons/woowacourse-kotlin-lotto/kimhm0728/94-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +176 -0
  472. package/lessons/woowacourse-kotlin-lotto/kkosang/85-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +145 -0
  473. package/lessons/woowacourse-kotlin-lotto/kmkim2689/70-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +97 -0
  474. package/lessons/woowacourse-kotlin-lotto/kmkim2689/82-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +157 -0
  475. package/lessons/woowacourse-kotlin-lotto/krrong/19-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +161 -0
  476. package/lessons/woowacourse-kotlin-lotto/krrong/41-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +73 -0
  477. package/lessons/woowacourse-kotlin-lotto/m6z1/105-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +67 -0
  478. package/lessons/woowacourse-kotlin-lotto/m6z1/151-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +104 -0
  479. package/lessons/woowacourse-kotlin-lotto/medAndro/127-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +186 -0
  480. package/lessons/woowacourse-kotlin-lotto/medAndro/130-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +132 -0
  481. package/lessons/woowacourse-kotlin-lotto/moondev03/110-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +66 -0
  482. package/lessons/woowacourse-kotlin-lotto/moondev03/141-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +155 -0
  483. package/lessons/woowacourse-kotlin-lotto/murjune/69-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +143 -0
  484. package/lessons/woowacourse-kotlin-lotto/murjune/90-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +177 -0
  485. package/lessons/woowacourse-kotlin-lotto/no1msh/20-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +69 -0
  486. package/lessons/woowacourse-kotlin-lotto/no1msh/46-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +143 -0
  487. package/lessons/woowacourse-kotlin-lotto/otter66/13-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +178 -0
  488. package/lessons/woowacourse-kotlin-lotto/otter66/53-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +160 -0
  489. package/lessons/woowacourse-kotlin-lotto/oungsi2000/126-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +71 -0
  490. package/lessons/woowacourse-kotlin-lotto/oungsi2000/149-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +56 -0
  491. package/lessons/woowacourse-kotlin-lotto/parkjiminnnn/117-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +129 -0
  492. package/lessons/woowacourse-kotlin-lotto/parkjiminnnn/146-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +173 -0
  493. package/lessons/woowacourse-kotlin-lotto/pingu244/33-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +21 -0
  494. package/lessons/woowacourse-kotlin-lotto/pingu244/54-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +30 -0
  495. package/lessons/woowacourse-kotlin-lotto/pingu244/7-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +19 -0
  496. package/lessons/woowacourse-kotlin-lotto/re4rk/31-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +143 -0
  497. package/lessons/woowacourse-kotlin-lotto/re4rk/4-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +66 -0
  498. package/lessons/woowacourse-kotlin-lotto/rhkrwngud445/23-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +26 -0
  499. package/lessons/woowacourse-kotlin-lotto/rhkrwngud445/38-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +129 -0
  500. package/lessons/woowacourse-kotlin-lotto/rhthrhrl0/21-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +146 -0
  501. package/lessons/woowacourse-kotlin-lotto/rhthrhrl0/36-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +150 -0
  502. package/lessons/woowacourse-kotlin-lotto/rosemin928/123-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +179 -0
  503. package/lessons/woowacourse-kotlin-lotto/rosemin928/140-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +126 -0
  504. package/lessons/woowacourse-kotlin-lotto/s6m1n/103-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +119 -0
  505. package/lessons/woowacourse-kotlin-lotto/s6m1n/66-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +118 -0
  506. package/lessons/woowacourse-kotlin-lotto/s9hn/18-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +112 -0
  507. package/lessons/woowacourse-kotlin-lotto/sh1mj1/75-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +104 -0
  508. package/lessons/woowacourse-kotlin-lotto/sh1mj1/91-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +140 -0
  509. package/lessons/woowacourse-kotlin-lotto/songpink/65-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +96 -0
  510. package/lessons/woowacourse-kotlin-lotto/songpink/99-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +64 -0
  511. package/lessons/woowacourse-kotlin-lotto/sujin9/10-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +20 -0
  512. package/lessons/woowacourse-kotlin-lotto/sujin9/35-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +124 -0
  513. package/lessons/woowacourse-kotlin-lotto/tmdgh1592/22-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +30 -0
  514. package/lessons/woowacourse-kotlin-lotto/tmdgh1592/30-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +20 -0
  515. package/lessons/woowacourse-kotlin-lotto/tobae-time/114-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +158 -0
  516. package/lessons/woowacourse-kotlin-lotto/tobae-time/145-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +120 -0
  517. package/lessons/woowacourse-kotlin-lotto/whk06061/42-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +21 -0
  518. package/lessons/woowacourse-kotlin-lotto/whk06061/9-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +89 -0
  519. package/lessons/woowacourse-kotlin-lotto/wondroid-world/118-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +100 -0
  520. package/lessons/woowacourse-kotlin-lotto/wondroid-world/150-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +142 -0
  521. package/lessons/woowacourse-kotlin-lotto/yrsel/108-1/353/213/250/352/263/204-/353/241/234/353/230/220.md +124 -0
  522. package/lessons/woowacourse-kotlin-lotto/yrsel/143-2/353/213/250/352/263/204-/353/241/234/353/230/220.md +108 -0
  523. package/lessons/woowacourse-racingcar/2chang5/33-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +56 -0
  524. package/lessons/woowacourse-racingcar/2chang5/75-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  525. package/lessons/woowacourse-racingcar/CFalws/85-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +56 -0
  526. package/lessons/woowacourse-racingcar/Choisehyeon/46-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +61 -0
  527. package/lessons/woowacourse-racingcar/DYGames/49-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +62 -0
  528. package/lessons/woowacourse-racingcar/EmilyCh0/40-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +64 -0
  529. package/lessons/woowacourse-racingcar/EmilyCh0/57-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  530. package/lessons/woowacourse-racingcar/HamBeomJoon/137-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  531. package/lessons/woowacourse-racingcar/HamBeomJoon/170-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  532. package/lessons/woowacourse-racingcar/Hevton/106-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  533. package/lessons/woowacourse-racingcar/Hevton/118-/353/246/254/355/214/251/355/204/260/353/247/201.md +51 -0
  534. package/lessons/woowacourse-racingcar/Hogu59/108-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +56 -0
  535. package/lessons/woowacourse-racingcar/Hogu59/125-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  536. package/lessons/woowacourse-racingcar/JoYehyun99/111-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  537. package/lessons/woowacourse-racingcar/JoYehyun99/88-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +45 -0
  538. package/lessons/woowacourse-racingcar/Junyoung-WON/127-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  539. package/lessons/woowacourse-racingcar/Junyoung-WON/90-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  540. package/lessons/woowacourse-racingcar/Leeyerin0210/133-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  541. package/lessons/woowacourse-racingcar/Leeyerin0210/159-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  542. package/lessons/woowacourse-racingcar/PROGRESS.md +94 -0
  543. package/lessons/woowacourse-racingcar/README.md +69 -0
  544. package/lessons/woowacourse-racingcar/RightHennessy/51-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  545. package/lessons/woowacourse-racingcar/RightHennessy/58-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  546. package/lessons/woowacourse-racingcar/RunaNam/81-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +44 -0
  547. package/lessons/woowacourse-racingcar/SUMMARY.md +339 -0
  548. package/lessons/woowacourse-racingcar/SeongHoonC/37-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  549. package/lessons/woowacourse-racingcar/SeongHoonC/66-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  550. package/lessons/woowacourse-racingcar/Songusika/84-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  551. package/lessons/woowacourse-racingcar/Yunseok-Nam/114-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +43 -0
  552. package/lessons/woowacourse-racingcar/Yunseok-Nam/96-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  553. package/lessons/woowacourse-racingcar/aprilgom/130-/353/246/254/355/214/251/355/204/260/353/247/201.md +52 -0
  554. package/lessons/woowacourse-racingcar/aprilgom/97-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  555. package/lessons/woowacourse-racingcar/awesomeo184/23-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  556. package/lessons/woowacourse-racingcar/boogi-woogi/35-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +62 -0
  557. package/lessons/woowacourse-racingcar/boogi-woogi/59-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  558. package/lessons/woowacourse-racingcar/briandr97/54-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  559. package/lessons/woowacourse-racingcar/chaehyuns/131-/353/246/254/355/214/251/355/204/260/353/247/201.md +49 -0
  560. package/lessons/woowacourse-racingcar/chaehyuns/99-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +52 -0
  561. package/lessons/woowacourse-racingcar/chanho0908/147-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  562. package/lessons/woowacourse-racingcar/chanho0908/160-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  563. package/lessons/woowacourse-racingcar/chws0508/45-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +61 -0
  564. package/lessons/woowacourse-racingcar/chws0508/73-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +46 -0
  565. package/lessons/woowacourse-racingcar/cucumber99/132-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  566. package/lessons/woowacourse-racingcar/cucumber99/177-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  567. package/lessons/woowacourse-racingcar/devfeijoa/146-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  568. package/lessons/woowacourse-racingcar/doabletuple/149-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  569. package/lessons/woowacourse-racingcar/doabletuple/175-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  570. package/lessons/woowacourse-racingcar/donghyun81/154-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +58 -0
  571. package/lessons/woowacourse-racingcar/dpcks0509/103-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  572. package/lessons/woowacourse-racingcar/dpcks0509/112-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  573. package/lessons/woowacourse-racingcar/drunkenhw/82-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  574. package/lessons/woowacourse-racingcar/etama123/145-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  575. package/lessons/woowacourse-racingcar/gaeun5744/124-/353/246/254/355/214/251/355/204/260/353/247/201.md +53 -0
  576. package/lessons/woowacourse-racingcar/gaeun5744/93-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  577. package/lessons/woowacourse-racingcar/gahyunkim/134-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  578. package/lessons/woowacourse-racingcar/gahyunkim/164-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  579. package/lessons/woowacourse-racingcar/giovannijunseokim/140-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  580. package/lessons/woowacourse-racingcar/haeum808/101-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  581. package/lessons/woowacourse-racingcar/haeum808/129-/353/246/254/355/214/251/355/204/260/353/247/201.md +46 -0
  582. package/lessons/woowacourse-racingcar/hwannow/141-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +56 -0
  583. package/lessons/woowacourse-racingcar/hwannow/157-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +45 -0
  584. package/lessons/woowacourse-racingcar/hxeyexn/109-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +61 -0
  585. package/lessons/woowacourse-racingcar/hxeyexn/128-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  586. package/lessons/woowacourse-racingcar/hyemdooly/50-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  587. package/lessons/woowacourse-racingcar/hyemdooly/68-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  588. package/lessons/woowacourse-racingcar/hyunji1203/29-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  589. package/lessons/woowacourse-racingcar/hyunji1203/60-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  590. package/lessons/woowacourse-racingcar/ii2001/102-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +42 -0
  591. package/lessons/woowacourse-racingcar/ii2001/122-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  592. package/lessons/woowacourse-racingcar/ijh1298/144-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  593. package/lessons/woowacourse-racingcar/injoon2019/24-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +58 -0
  594. package/lessons/woowacourse-racingcar/inseonyun/44-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  595. package/lessons/woowacourse-racingcar/inseonyun/76-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  596. package/lessons/woowacourse-racingcar/ippnsj/36-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  597. package/lessons/woowacourse-racingcar/ippnsj/67-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  598. package/lessons/woowacourse-racingcar/jaeyeongjo/110-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +39 -0
  599. package/lessons/woowacourse-racingcar/jaeyeongjo/89-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +46 -0
  600. package/lessons/woowacourse-racingcar/jinuemong/104-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  601. package/lessons/woowacourse-racingcar/jinuemong/117-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +42 -0
  602. package/lessons/woowacourse-racingcar/jiyuneel/142-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  603. package/lessons/woowacourse-racingcar/junjange/113-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +41 -0
  604. package/lessons/woowacourse-racingcar/junjange/87-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +39 -0
  605. package/lessons/woowacourse-racingcar/junseo511/148-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +52 -0
  606. package/lessons/woowacourse-racingcar/junseo511/165-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +51 -0
  607. package/lessons/woowacourse-racingcar/ki960213/32-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  608. package/lessons/woowacourse-racingcar/ki960213/63-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +51 -0
  609. package/lessons/woowacourse-racingcar/kimhm0728/100-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +52 -0
  610. package/lessons/woowacourse-racingcar/kimhm0728/116-/353/246/254/355/214/251/355/204/260/353/247/201.md +54 -0
  611. package/lessons/woowacourse-racingcar/kkosang/105-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  612. package/lessons/woowacourse-racingcar/kkosang/126-/353/246/254/355/214/251/355/204/260/353/247/201.md +53 -0
  613. package/lessons/woowacourse-racingcar/kmkim2689/123-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  614. package/lessons/woowacourse-racingcar/kmkim2689/92-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  615. package/lessons/woowacourse-racingcar/krrong/34-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +63 -0
  616. package/lessons/woowacourse-racingcar/m6z1/150-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  617. package/lessons/woowacourse-racingcar/m6z1/156-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +40 -0
  618. package/lessons/woowacourse-racingcar/medAndro/153-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  619. package/lessons/woowacourse-racingcar/moondev03/135-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +57 -0
  620. package/lessons/woowacourse-racingcar/moondev03/161-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +52 -0
  621. package/lessons/woowacourse-racingcar/murjune/121-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  622. package/lessons/woowacourse-racingcar/murjune/95-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  623. package/lessons/woowacourse-racingcar/no1msh/43-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  624. package/lessons/woowacourse-racingcar/no1msh/69-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  625. package/lessons/woowacourse-racingcar/otter66/48-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  626. package/lessons/woowacourse-racingcar/otter66/77-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +52 -0
  627. package/lessons/woowacourse-racingcar/oungsi2000/152-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +56 -0
  628. package/lessons/woowacourse-racingcar/oungsi2000/187-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  629. package/lessons/woowacourse-racingcar/parkjiminnnn/143-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +58 -0
  630. package/lessons/woowacourse-racingcar/parkjiminnnn/158-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  631. package/lessons/woowacourse-racingcar/pingu244/38-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +58 -0
  632. package/lessons/woowacourse-racingcar/pingu244/62-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  633. package/lessons/woowacourse-racingcar/re4rk/28-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +60 -0
  634. package/lessons/woowacourse-racingcar/re4rk/55-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  635. package/lessons/woowacourse-racingcar/rhkrwngud445/42-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  636. package/lessons/woowacourse-racingcar/rhkrwngud445/74-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +47 -0
  637. package/lessons/woowacourse-racingcar/rhthrhrl0/31-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +43 -0
  638. package/lessons/woowacourse-racingcar/rosemin928/138-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  639. package/lessons/woowacourse-racingcar/rosemin928/171-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +38 -0
  640. package/lessons/woowacourse-racingcar/s6m1n/120-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +54 -0
  641. package/lessons/woowacourse-racingcar/s6m1n/91-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +62 -0
  642. package/lessons/woowacourse-racingcar/s9hn/53-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +44 -0
  643. package/lessons/woowacourse-racingcar/s9hn/78-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +43 -0
  644. package/lessons/woowacourse-racingcar/sh1mj1/107-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  645. package/lessons/woowacourse-racingcar/sh1mj1/115-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +61 -0
  646. package/lessons/woowacourse-racingcar/songpink/119-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +51 -0
  647. package/lessons/woowacourse-racingcar/songpink/98-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +55 -0
  648. package/lessons/woowacourse-racingcar/sujin9/52-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +48 -0
  649. package/lessons/woowacourse-racingcar/sujin9/61-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +47 -0
  650. package/lessons/woowacourse-racingcar/tmdgh1592/47-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  651. package/lessons/woowacourse-racingcar/tmdgh1592/64-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  652. package/lessons/woowacourse-racingcar/tobae-time/151-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +51 -0
  653. package/lessons/woowacourse-racingcar/tobae-time/167-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +43 -0
  654. package/lessons/woowacourse-racingcar/whk06061/41-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +58 -0
  655. package/lessons/woowacourse-racingcar/wondroid-world/136-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +49 -0
  656. package/lessons/woowacourse-racingcar/wondroid-world/166-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +50 -0
  657. package/lessons/woowacourse-racingcar/yrsel/139-1/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +53 -0
  658. package/lessons/woowacourse-racingcar/yujamint/83-2/353/213/250/352/263/204-/354/236/220/353/217/231/354/260/250-/352/262/275/354/243/274.md +59 -0
  659. package/package.json +46 -0
  660. package/skills/oh-my-oop/SKILL.md +39 -0
@@ -0,0 +1,516 @@
1
+ # PR #108 — [블랙잭 1단계] 시아 미션
2
+
3
+ - **Reviewee:** [@Leeyerin0210](https://github.com/Leeyerin0210)
4
+ - **PR:** https://github.com/woowacourse/kotlin-blackjack/pull/108
5
+ - **단계:** 1단계
6
+ - **리뷰어:** @malibinYun (말리빈)
7
+ - **라인 코멘트:** 30 스레드 / 62 코멘트 (리뷰어·리뷰이 다회 핑퐁 다수)
8
+
9
+ ## 잘한 점 (설계 관점)
10
+
11
+ - **PR 본문 자가 토론 — 딜러 이름 + Hand 책임 분리** — 학생이 *딜러 이름*에 대해 4가지 옵션(없음 → 출력시 "딜러" / 기본값 "딜러" / 타입 enum / 속성 비교)을 *자가 정리한 후* 4번을 *"모델과 뷰 결합"* 우려로 자가 제외. *Hand가 카드 보관 + 점수 계산 두 책임을 가지는가*도 학생이 *자가 의문*. PR 전체에 *학생 자가 의문 → 말리빈 메타 질문 → 자가 답변* 패턴 일관.
12
+ - **`ShuffleStrategy` 인터페이스로 셔플 분리 → 테스트 가능 `CardDeck`** — 말리빈의 *"CardDeck 객체는 테스트가 불가능한 구조이네요!"* 한 줄 지적에 대해 *전략 패턴*으로 분리. `class CardDeck(val shuffleStrategy: ShuffleStrategy = RandomShuffle())` — 기본값 + 테스트 시 *순서 고정 셔플* 주입 가능. 말리빈 자가 칭찬: *"랜덤의 요소를 인터페이스-구현체 구조로 잘 쪼개주셨네요 👍"*.
13
+ - **블랙잭 룰 정확성 자가 학습 — *"2장만으로 21이 나오면 블랙잭"*** — 처음에는 *점수 비교만*으로 승부 판정. 말리빈의 *"단순히 점수의 크고 작음 만을 비교해서는 승패를 판별할 수 없답니다. 블랙잭 도메인에 대해 더 잘 알아보세요"* 한 줄로 학생이 *블랙잭 룰 자가 학습* → *2장 + 21*만 진짜 블랙잭으로 자가 반영. 학생 자가 인용: *"블랙잭 게임이 왜 블랙잭인가 했는데, 2장만으로 21점이 나오면 블랙잭이라 하는 걸 알게 되었습니다."* PR #128·#135·#114·#124 와 같은 결.
14
+ - **6덱 + 자동 재셔플 — 카드 부족 → 게임 강제 종료 회피 후속 반영** — 말리빈의 *"한창 게임이 진행되는 도중에 카드가 부족해 게임이 종료되는 것은, 정상적인 게임 프로그램일까요?"* + *"카지노에서 덱 6벌이 사라졌으니, 카지노 문 닫고 손님들을 모두 쫓아내지 않는 것 처럼, 게임이 강제 종료되는 것은 문제라고 생각해요"* 진단에 대해 *6덱*으로 늘렸다가 *그래도 무한 게임 보장 못 함* 지적 후 *"카드 없을 경우, 새 기본 덱을 가져와서 무한 뽑을 수 있도록"* 자가 반영. *현실 카지노 = 6시간 게임* 멘탈 모델로 학생 사고 전환.
15
+ - **Effective Kotlin 자가 학습 — Item 4/14 정리 후 자가 답변** — 말리빈의 *"멤버변수와 메서드의 리턴타입은 모두 명시해주는 것은 어떨까요? ... Effective Kotlin Item 4·14 참고"* 권고에 학생이 *책 본인 정리* → *자가 답변* → *Unit 예외 의문* → *말리빈 보강*. *외부 참조 학습 → 자가 정리 → 자가 의문* 흐름이 모범.
16
+ - **`invoke` 팩토리 함수로 카드 캐싱 노출** — 말리빈의 *"덱에서 미리 생성해둔 것을 아는 사람은 작성한 사람 뿐이겠지요. 다른 개발자가 카드를 생성하는 로직을 활용해야할 때, 카드의 생성자를 바로 불러버리는 것이 가장 간편한 방법은 아닐지요"* 메타 질문에 대해 `operator fun invoke(rank, suit)` 로 *`Card(...)` 호출 자체가 캐시 lookup* 으로 자가 반영. *"다른 개발자가 생성자를 바로 불러도 기존 캐시된 카드들을 부를 수 있도록"* 자가 답변.
17
+ - **`BlackjackEngine` 도메인 객체로 게임 진행 책임 이전** — *"딜러와 플레이어가 카드를 뽑는 로직은 컨트롤러의 역할일까요?"* + *"게임의 진행 일련의 과정도 컨트롤러의 역할일지 고민해보세요"* 두 단계 의문에 대해 *`BlackjackEngine` 도메인 객체 신설* + *드로우 책임 이전*. **PR #124 (모찌) 의 `BlackjackController god-object` 와 정확히 같은 진단에 대한 *반대편 모범 답안*** — 시아는 *Engine 객체 신설*로 1단계 안에서 일부 해소.
18
+
19
+ ## 못한 점 (설계 관점)
20
+
21
+ ### 1. `Card.invoke` 와 *생성자 호출 가능성* 의 모호함
22
+
23
+ ```kotlin
24
+ class Card(val rank: CardRank, val suit: CardSuit) {
25
+ companion object {
26
+ val SINGLE_DECK = CardRank.entries.flatMap { rank ->
27
+ CardSuit.entries.map { suit -> Card(rank, suit) }
28
+ }
29
+
30
+ operator fun invoke(rank: CardRank, suit: CardSuit): Card {
31
+ return SINGLE_DECK.findLast { it.rank == rank && it.suit == suit }
32
+ ?: throw IllegalArgumentException("[ERROR] 잘못된 카드 번호나 문양입니다.")
33
+ }
34
+ }
35
+ }
36
+ ```
37
+
38
+ 말리빈 (Card.kt:18 — 미해결): *"카드를 가져오려면 아래 형태로 작성해야겠네요. `Card(CardRank.ACE, CardSuit.SPADE)`. 이것은 생성자로 호출한 것인지 invoke 함수를 호출한 것인지 저도 모르겠는데요? Java의 바이트코드를 뜯어보지 않는 이상 어떤 것을 호출했는지 알기가 매우 어려워요. **생성자를 호출하는 케이스가 된다면, 중복된 값을 가지는 인스턴스를 생성할 수 있는 단점이 여전히 있겠어요.** invoke함수를 선택한 이유가 있을까요? 이팩티브 코틀린의 팩토리 함수에 대해 알아보셔도 좋겠어요."*
39
+
40
+ → **`operator fun invoke` + `public class Card` 가 두 길**. *Card(rank, suit) 호출*이 *생성자*에 가는지 *invoke*에 가는지 *Kotlin 컴파일러 우선순위*에 묻혀 있음. *생성자가 우선*이라 *invoke가 잡히지 않을 가능성*. *private constructor + companion fun of(...)* 패턴이 *팩토리 함수의 정공*. `class Card private constructor(...) { companion object { fun of(rank, suit): Card = SINGLE_DECK.first { it.rank == rank && it.suit == suit } } }`.
41
+
42
+ 또한 `SINGLE_DECK.findLast` 의 `findLast` 는 *동일 카드가 여러 개*일 때 *마지막*을 찾는 의미인데 *SINGLE_DECK 자체가 unique* 이므로 `first` 가 자연. *naming 부조화*.
43
+
44
+ ### 2. `Hand` 의 `BUST_SCORE = -1` 센티넬 + `maxOf` 트릭
45
+
46
+ ```kotlin
47
+ class Hand(firstCard: List<Card>) {
48
+ private val _cards: MutableList<Card> = firstCard.toMutableList()
49
+ val cards: List<Card> get() = _cards.toList()
50
+
51
+ fun isBust(): Boolean = score() == BUST_SCORE
52
+
53
+ fun score(): Int {
54
+ val baseScore = cards.sumOf { card -> card.rank.score }
55
+ return maxOf(baseScore.formatIfBust(), maxScoreWithAce(baseScore).formatIfBust())
56
+ }
57
+
58
+ private fun maxScoreWithAce(hardScore: Int): Int {
59
+ val containsAce = cards.any { card -> card.rank == CardRank.ACE }
60
+ return if (containsAce) hardScore + SOFT_OFFSET_SCORE else hardScore
61
+ }
62
+
63
+ private fun Int.formatIfBust(): Int = if (this > BUST_CRITERIA) BUST_SCORE else this
64
+
65
+ companion object {
66
+ private const val BUST_SCORE = -1
67
+ private const val BUST_CRITERIA = 21
68
+ private const val SOFT_OFFSET_SCORE = 10
69
+ }
70
+ }
71
+ ```
72
+
73
+ → **Bust 점수를 *-1* 센티넬로 표현 + `maxOf` 로 둘 중 큰 값**. 사고 흐름:
74
+
75
+ - baseScore = 카드 점수 합 (Ace는 1)
76
+ - maxScoreWithAce = Ace 있으면 baseScore + 10
77
+ - 둘 다 21 초과면 → -1 (BUST_SCORE)
78
+ - maxOf 로 둘 중 큰 값
79
+
80
+ 이 트릭이 *작동은 함* (`maxOf(-1, 20) = 20`, `maxOf(-1, -1) = -1`). 다만:
81
+
82
+ 1. **`score() == BUST_SCORE` 로 Bust 판정** — *점수 -1이 Bust*라는 매핑이 *Hand 외부에 새지 않아야* 하는데 `isBust` 가 *내부 의미를 외부 의미와 연결*. *`score() < 0` = Bust*가 *암묵적 invariant*.
83
+ 2. **`score()` 가 *Bust일 때 -1 반환*** — 호출자가 *점수로 비교*하려고 `score()`를 부르면 *-1을 받고 잘못된 분기*. *Bust 분리* 가 *isBust 메시지로 먼저 묻기* 가 강제됨.
84
+ 3. **이름 — `BUST_CRITERIA=21` 은 *Bust 기준이 아니라 블랙잭 상한***. `MAX_SCORE = 21` / `BUST_SENTINEL = -1` 같은 이름이 자연.
85
+ 4. **두 점수 후보 비교** — *`maxOf(baseScore, baseScore + 10)`* 는 *baseScore + 10 > baseScore 항상*. *Ace 있으면 +10 후 21 이하인지만 보면 됨*. *현재 트릭*은 *둘 다 Bust면 -1, 한쪽만 Bust면 다른 쪽*. 결과는 맞으나 *Ace 1 기본 + 단일 +10 if (sum + 10 ≤ 21)* 패턴이 *모두 한 줄*. 학생이 *Bust 양가성*을 *센티넬 + maxOf*로 풀어 *복잡도가 늘었다*.
86
+
87
+ 말리빈은 *softScore/hardScore 이름*만 지적 (못한 점 §3 참고). *센티넬 -1 트릭* 자체는 미해결로 남음 — *2단계에서 다시 손볼 신호*.
88
+
89
+ ### 3. `softScore` / `hardScore` 모호 명명 → 후속 자가 반영
90
+
91
+ ```kotlin
92
+ // 초기 (예상)
93
+ private fun softScore(): Int { ... }
94
+ private fun hardScore(): Int { ... }
95
+ ```
96
+
97
+ 말리빈: *"다른 개발자들도 softScore와 hardScore가 무슨 뜻인지 한 번에 유추할 수 있을까요?"*
98
+
99
+ 학생 자가 답변 (커밋 `f62c66c`): *"처음 함수 이름을 작성했을 때는 단순계산 이란 뜻으로 hard, 그의 반대인 soft라고 작성했으나, 다시 보니 확실히 확인하기 어려울 것 같아, 이름에 확실히 뜻이 들어가도록 수정했습니다."*
100
+
101
+ → **블랙잭 도메인 어휘는 *카지노 표준*** — 카지노에서는 *soft 17 / hard 17*이 표준 용어 (Ace를 11로 셌을 때 / Ace를 1로 셌을 때). 학생은 *"단순계산 = hard / 반대 = soft"* 라고 *임의 매핑*. *카지노 표준 어휘*라도 *블랙잭 미숙자*에겐 모호. *`baseScore`/`maxScoreWithAce`* 같은 *구현 의미가 보이는 이름*이 자연. *도메인 어휘 차용 vs 구현 의미 명시* 의 트레이드오프 — *내부 함수는 구현 의미*가 안전, *외부 API는 도메인 어휘*가 자연.
102
+
103
+ ### 4. `Hand(firstCard: List<Card>)` 생성자 파라미터 이름 — *list가 firstCard?*
104
+
105
+ ```kotlin
106
+ class Hand(firstCard: List<Card>) {
107
+ private val _cards: MutableList<Card> = firstCard.toMutableList()
108
+ ...
109
+ }
110
+ ```
111
+
112
+ → **`firstCard: List<Card>` 라는 모순**. *first* + *복수형 List<Card>* 가 *카드 1장 vs 카드 여러 장* 의 혼란. *`initialCards: List<Card>` / `cards: List<Card>`* 가 자연. *Player/Dealer 의 `firstCard: List<Card>` 멤버*도 같은 모순.
113
+
114
+ ### 5. `Player.firstCard` 멤버 + `Dealer.firstCard` 멤버 — *초기값을 멤버로 보유*
115
+
116
+ ```kotlin
117
+ class Player(val name: String, val firstCard: List<Card>) : Participant(firstCard)
118
+
119
+ class Dealer(val firstCard: List<Card>, val name: String = DEALER_NAME) : Participant(firstCard) {
120
+ fun getAdditionalDrawCount(): Int {
121
+ return hand.getHandCount() - firstCard.size // ⚠ 초기 카드 수 vs 현재 손패 수
122
+ }
123
+ ...
124
+ }
125
+ ```
126
+
127
+ 말리빈 (Player.kt:6 — 미해결): *"firstCard가 멤버로 선언될 필요가 있을지 고민해보세요. 또, 처음부터 Hand를 갖게하는 것도 자연스럽다는 생각이 드네요"*
128
+
129
+ → **`firstCard`를 멤버로 보유 = 초기 상태를 영구 보관**. *초기 카드 = 생성자 인자*면 *Hand 만들고 끝* — Player/Dealer 가 *기억할 필요 없음*. *`Dealer.getAdditionalDrawCount`* 가 *현재 손패 수 - 초기 카드 수*로 *추가 뽑은 수*를 계산하는데, 이건 *Dealer 가 자기 초기 상태와 현재 상태를 비교*하는 *시간 비교*. *추가 뽑은 수 자체가 도메인 메시지가 아니라 출력용 카운터*.
130
+
131
+ 말리빈 (Dealer.kt — 미해결): *"반환 값인 Int가 어떤 값을 의미하는지 유추하기는 어려워보여요. 나아가서, 어떠한 플랫폼의 (콘솔)의 영향으로 이렇게 구성했다는 느낌이 강하게 드네요. 도메인에서 이러한 것을 알아야할지 고민해보세요"*
132
+
133
+ 학생 자가 답변 (커밋 `a94d03f`): *"함수에서 뽑는 것과 몇개 뽑았는지 반환하기 두가지의 기능을 모두 제공하려고 해서 이런 문제가 생긴 것 같습니다. 뽑는 건 뽑기만 할 수 있도록 하고, 몇개 뽑았는지 반환하는 것은 메세지를 던져서 반환할 수 있도록 하였습니다."*
134
+
135
+ → *뽑기 + 카운트 두 책임 분리* 자가 답변. *firstCard 멤버 보유* 자체는 여전히 미해결.
136
+
137
+ ### 6. `Participant` 추상 클래스 — *추상이 하나도 없는데 abstract 사용*
138
+
139
+ ```kotlin
140
+ abstract class Participant(firstCard: List<Card>) {
141
+ val hand: Hand = Hand(firstCard)
142
+
143
+ fun draw(cardDeck: CardDeck) {
144
+ hand.add(cardDeck.draw())
145
+ }
146
+
147
+ fun getHandSize(): Int = hand.getHandCount()
148
+ fun getScore(): Int = hand.score()
149
+ }
150
+ ```
151
+
152
+ 학생 자가 답변 (Participant.kt 첫 코멘트): *"플레이어와 딜러 모두 참가자에 속하고, 참가자가 모두 공통으로 가져야 할 기능들이 있기 때문에 사용하는 것이 좋다고 생각했습니다."*
153
+
154
+ 말리빈 (후속): *"그렇다면, open class와 interface를 활용하는 것과 현재의 차이점은 무엇인가요? 그리고 나서 다시 한 번 생각해주세요. 그 둘을 사용하지 않고, 여기에서 abstract 키워드를 사용한 이유는 무엇인가요?"*
155
+
156
+ 학생: *"Open 클래스: 인스턴스화가 가능하므로 추상적인 개념(참가자)을 표현하는 데 적합하지 않습니다. ... Interface: 공통적인 메서드를 정의하는 데는 유용하지만, 상태나 생성자 로직을 포함할 수 없어서 ... 참가자는 모두 자신의 핸드를 가지고 있기 때문에, 한계가 명확하다고 생각했습니다."*
157
+
158
+ 말리빈 (재반박, Participant.kt:5 — 미해결): *"생성자 로직을 포함할 수 없는 것은 공감이돼요. 그런데 참가자가 모두 자신의 핸드를 가지고 있기 때문에 한계가 명확한 것은 공감이 되지 않아요. 인터페이스에서 hand를 반드시 구현해야한다는 것을 명시하면 모두 Hand를 가지게 만들 수 있으니까요. 현 코드를 interface로 전환하는 건 완벽하게 불가능한가요? **abstract class는 고장 난 부분은 당신이 채워 넣으라 라는 의미에 가깝다고 생각해요. 그런데 여기에는 abstract할 게 하나도 없으니, abstract를 사용할 이유가 없다고 생각해요 :)**"*
159
+
160
+ → **`abstract` 키워드의 의미 = "고장 난 부분(abstract method)을 자식이 채운다"**. *abstract method 0 + open property 0* 인 *Participant* 는 *생성자 로직을 공유하는 부모 클래스*일 뿐. *`open class` 면 동일 효과 + 인스턴스화 막으려면 `sealed class`*. *Kotlin sealed class* 가 *Player/Dealer 두 자식만 허용*하면서 *인스턴스화 불가*도 만족. PR #28·#135·#114·#125 와 같은 결 (`open class` vs `abstract class` vs `sealed class` 차이).
161
+
162
+ 학생의 *"Interface는 상태/생성자 로직 포함 불가"* 도 *Kotlin interface property* 로 우회 가능 (`interface Participant { val hand: Hand }`). *"한계가 명확"* 이라는 표현이 *Kotlin 기능 미숙*에서 옴.
163
+
164
+ ### 7. `CalculateResult` object — *정적 계산기 = 책임 누수*
165
+
166
+ ```kotlin
167
+ object CalculateResult {
168
+ private fun getResult(oneSelf: Participant, other: Participant): WinningResult {
169
+ val oneSelfBlackjack = oneSelf.getHandSize() == 2 && oneSelf.getScore() == 21
170
+ val otherBlackjack = other.getHandSize() == 2 && other.getScore() == 21
171
+
172
+ return when {
173
+ oneSelfBlackjack && otherBlackjack -> PUSH
174
+ oneSelfBlackjack -> WIN
175
+ otherBlackjack -> LOSE
176
+ oneSelf.getScore() > other.getScore() -> WIN
177
+ oneSelf.getScore() < other.getScore() -> LOSE
178
+ else -> PUSH
179
+ }
180
+ }
181
+
182
+ fun getUserResult(dealer: Dealer, player: Player): WinningResult = getResult(player, dealer)
183
+ fun getDealerResult(dealer: Dealer, player: Player): WinningResult = getResult(dealer, player)
184
+ }
185
+ ```
186
+
187
+ 말리빈 (CalculateResult.kt — 미해결): *"어떤 계산기가 딜러와 플레이어를 앞에 두고 카드를 비교해주면서 결과를 내어줄 수도 있겠어요. 현실세계를 반영해보는 건 어떨까요? **이겼는지 졌는지 알려주는 건 누가 하면 적절할 역할일지 고민해보세요** :)"*
188
+
189
+ → **`object CalculateResult` = 정적 헬퍼로 비교 책임 격리**. *Tell-Don't-Ask* 위반 — *`oneSelf.getHandSize()` / `oneSelf.getScore()`* 로 *자기 정보를 빼서* *계산기가 비교*. *Participant.compete(other: Participant): WinningResult* 메시지면 *participant가 자기 결과를 알려줌*. PR #124 (모찌) 의 `GameResult.of(score, score)` 와 *정확히 같은 안티패턴*.
190
+
191
+ 또한 *`getUserResult` / `getDealerResult` 가 같은 함수의 인자 순서만 바꾼 래퍼* — *둘 다 필요한가?* `compete` 가 *대칭적 메시지*면 *하나로 충분*.
192
+
193
+ 말리빈(WinningResult.kt 미해결): *"객체의 값을 직접 꺼내 비교하기보다, 객체에게 메시지를 던져보는 건 어떨까요? 그러다보면 이 점수 계산 로직이 어떠한 객체로 응집시킬 수 있어보이네요"* — *점수 비교 ≠ 점수 메시지*.
194
+
195
+ 학생 자가 답변 (커밋 `2fac65c`): *"로직을 분리하여 object로 만들었습니다! 메세지를 던지니 훨씬 더 객체끼리의 결합이 사는 듯 한 느낌이 드네요."* → **객체 → object 분리는 *Tell-Don't-Ask 해소*가 아님**. *`object`는 싱글톤 = 정적 헬퍼 = Ask 패턴*. 학생이 *"메시지 던지기"*를 *"호출자가 그 호출을 하는 행위 자체"* 로 오해. *진짜 메시지 던지기*는 *`participant.compete(other)`*.
196
+
197
+ ### 8. `Dealer.getWinDrawLossResult(players)` + `Players.results(dealer)` — *결과 집계 두 곳*
198
+
199
+ ```kotlin
200
+ // Dealer.kt
201
+ fun getWinDrawLossResult(players: Players): Map<WinningResult, Int> {
202
+ val result = WinningResult.entries.associateWith { INITIAL_SCORE }.toMutableMap()
203
+ players.value.forEach { player ->
204
+ val winningResult = CalculateResult.getDealerResult(this, player)
205
+ result[winningResult] = result.getOrDefault(winningResult, INITIAL_SCORE) + ADDITIONAL_RESULT_COUNT
206
+ }
207
+ return result.toMap()
208
+ }
209
+
210
+ // Players.kt
211
+ fun results(dealer: Dealer): Map<String, WinningResult> =
212
+ value.associate { player ->
213
+ player.name to CalculateResult.getUserResult(dealer, player)
214
+ }
215
+ ```
216
+
217
+ → **`Dealer` 가 *딜러의 W/D/L 카운트 집계* + `Players` 가 *플레이어별 결과 매핑***. *결과 집계 책임이 두 곳에 분산*. *`GameResults` 일급 컬렉션* 이 *전체 매치 결과를 한 번에 보유* 하고 *각 입장에서 필요한 view 제공* 이 자연.
218
+
219
+ 또한 `Dealer.getWinDrawLossResult(players)` 는 *Dealer가 모든 플레이어를 받아서 자기 결과 집계* — *Dealer가 자기 결과를 직접 계산*하기 위해 *전체 플레이어 의존*. *비대칭*. *Player는 자기 결과만 알면 되는데 Dealer는 전체*. *Match/Game 객체*가 *모든 비교를 끝내고 각자에게 결과 분배* 가 자연.
220
+
221
+ ### 9. `BlackjackEngine` — *god-object 분리 시도 미완성*
222
+
223
+ ```kotlin
224
+ class BlackjackEngine {
225
+ val cardDeck: CardDeck = CardDeck()
226
+
227
+ fun preparePlayers(names: List<String>): Players = Players(names.map { name -> Player(name, makeFirstCards()) })
228
+ fun prepareDealer(): Dealer = Dealer(makeFirstCards())
229
+ fun playerDraw(player: Player): Unit = player.draw(cardDeck)
230
+ fun dealerDraw(dealer: Dealer): Unit = dealer.drawUntilFinished(cardDeck)
231
+ fun makeFirstCards(): List<Card> = List(2) { cardDeck.draw() }
232
+ }
233
+ ```
234
+
235
+ 말리빈 (BlackjackEngine.kt:1 — 미해결): *"컨트롤러에 여전히 남아있는 게임 진행에 대한 역할들을 이 객체에 잘 옮겨내시길 기대할게요 :)"*
236
+
237
+ 말리빈 (BlackjackEngine.kt:13 — 미해결): *"메서드명은 동사로 시작하도록 작성해보세요 :)"* (`playerDraw` / `dealerDraw` 가 *명사+동사*)
238
+
239
+ 말리빈 (BlackjackEngine.kt:4 — 미해결): *"카드 덱도 주입 받게끔 만들어야 테스트 코드를 작성하기 원활해지겠어요 :)"*
240
+
241
+ → **`BlackjackEngine` 신설은 좋은 방향이지만 절반의 분리**:
242
+
243
+ 1. **`cardDeck = CardDeck()` 멤버 직접 생성** — 테스트 시 주입 불가. *생성자 인자*로 받아야 *순서 고정 셔플 테스트* 가능. 이미 `CardDeck`은 *전략 패턴*으로 주입 가능한데 *Engine* 단에서 다시 *new* 로 잠금.
244
+ 2. **`playerDraw(player)` / `dealerDraw(dealer)` 가 *Engine이 카드를 뽑아 Participant에 추가하는 절차*** — *진짜 메시지 던지기*면 *`player.draw(cardDeck)`* 만 호출자가 부르면 됨. *Engine 거치는 wrapper* 가 *간접 호출의 이중 단계*.
245
+ 3. **`makeFirstCards` 가 *2장 하드코딩*** — *블랙잭 초기 2장 룰*이 *Engine 메서드 내부에 상수*. *Dealer는 1장 공개 / 플레이어는 2장 공개* 라는 *공개 규칙*과 *분배 규칙*이 분리 안 됨.
246
+ 4. **`preparePlayers(names) / prepareDealer()` 의 *준비 책임이 Engine?*** — *Engine = 진행* 인지 *Engine = 준비 + 진행* 인지 경계 모호. *블랙잭 게임 = 한 번의 매치* 면 *생성자에서 다 받음*이 자연.
247
+
248
+ 말리빈의 *"컨트롤러에 여전히 남아있는 게임 진행 역할"* 은 *Engine 도입했지만 Controller 여전히 게임 진행 결정* 이라는 신호. 즉 *분리 시도 + 진짜 분리 실패*. PR #124 (모찌) 의 god-object 와 다른 양상이지만 *완전한 모범 답안은 아님*.
249
+
250
+ ### 10. `Hand(firstCard: List<Card>)` 생성 시 검증 부재
251
+
252
+ ```kotlin
253
+ class Hand(firstCard: List<Card>) {
254
+ private val _cards: MutableList<Card> = firstCard.toMutableList()
255
+ ...
256
+ }
257
+ ```
258
+
259
+ → **`Hand` 생성 시 *카드 0장도 허용***. *블랙잭 초기 2장 룰* 이 *Hand 자체에 강제되지 않음*. *Hand 가 자기 invariant 모름*. *0장 Hand 의 `score()` = 0* 인데 *블랙잭에서 0장 상태는 존재하지 않음*. *Engine.makeFirstCards()* 가 *항상 2장*을 만들어 *우회*하지만 *Hand 단독으로는 invariant 없음*.
260
+
261
+ 이건 PR #108 의 `Hand` 가 `Cards` 도메인 컬렉션 책임을 가진다는 점에서 *공통 점수 계산 + 카드 추가* 만 가지고 *블랙잭 초기 룰* 은 분리한 결과 — *Hand 가 블랙잭 hand가 아니라 generic card collection* 의 의도일 수도. 다만 *프로젝트 이름이 blackjack* 이고 *score() 가 21 기반* 이므로 *블랙잭에 결합* — *invariant 강제* 가 자연.
262
+
263
+ ### 11. `CardDeck.draw` 의 *자동 재셔플* — *현실은 좋으나 invariant 깨짐*
264
+
265
+ ```kotlin
266
+ class CardDeck(val shuffleStrategy: ShuffleStrategy = RandomShuffle()) {
267
+ private var cards = shuffleStrategy.shuffle(SINGLE_DECK)
268
+
269
+ fun draw(): Card {
270
+ return cards.removeFirstOrNull() ?: run {
271
+ cards = shuffleStrategy.shuffle(SINGLE_DECK)
272
+ return cards.removeFirst()
273
+ }
274
+ }
275
+ }
276
+ ```
277
+
278
+ → **카드 없으면 자동 새 덱 + 셔플 + draw**. *말리빈의 "카지노 = 무한 게임"* 모델에는 정합. 다만:
279
+
280
+ 1. **`cards = ... shuffle(SINGLE_DECK)`** — *`var cards`* 가 *멤버 재할당*. *멤버 immutability* 가 깨짐 (`var` + 재할당). *덱이 비면 새 덱*이 *같은 덱 객체가 채워지는가 / 새 덱 객체로 교체되는가*가 *동일성 의미*에 영향. 카지노에선 *카드를 다 쓰면 새 덱을 카지노 직원이 꺼냄* — *덱 객체 자체가 바뀜*이 자연. *코드 동작*과 *현실 metaphor* 정합.
281
+ 2. **`SINGLE_DECK` 재참조** — `SINGLE_DECK` 은 *companion val 52장 list*. *매 재셔플마다 같은 52장*. *6덱(312장) 의도*가 PR 본문에 있었으나 *코드는 1덱 반복 셔플*. *이전 라운드 사용 카드와 새 라운드 카드가 겹칠 가능성*. *현실 카지노는 6덱 6벌 진행 후 새 6덱* — *코드는 1덱 반복*.
282
+
283
+ ### 12. `RandomShuffle` 클래스 + `ShuffleStrategy` 인터페이스 — *외부 라이브러리 자제 권고*
284
+
285
+ ```kotlin
286
+ class RandomShuffle : ShuffleStrategy {
287
+ override fun shuffle(cardList: List<Card>) = cardList.shuffled().toMutableList()
288
+ }
289
+ ```
290
+
291
+ 말리빈 (CardDeck.kt — 미해결): *"코틀린에서는 최대한 코틀린 라이브러리를 활용해서 구현해보세요 :)"*
292
+
293
+ 학생 자가 답변 (커밋 `011cfff`) + 의문: *"구현해보았습니다! 혹시 외부 라이브러리를 자제해야하는 이유를 알 수 있을까요?"*
294
+
295
+ 말리빈: *"코틀린에서 기본 제공되는 것들이 있으니 최대한 그것을 활용해보시길 바라요 :). 굉장히 많은 것들을 제공해주니 이것들을 익숙하게 다루는 것도 중요하다 생각해서요. 더 많이 나아간다면, 코틀린은 JVM에서만 돌아가는 언어가 아니기 떄문이기도 해요. 어떠한 핵심 로직을 멀티플랫폼 어딘가에 이식해야할 때, JVM의 코드인 java 코드가 들어간다면, 이식할 때 번거로운 문제가 많이 생겨나겠지요"*
296
+
297
+ → **Kotlin Multiplatform 관점**. *Java import (e.g., `java.util.Random`, `Collections.shuffle`)* 가 들어가면 *Kotlin/JS, Kotlin/Native 이식 시 충돌*. *`List.shuffled()` 는 Kotlin stdlib* 이므로 안전. 학생이 *현재 stdlib `shuffled()` 사용 중* — 좋은 면. 말리빈의 권고는 *향후 외부 라이브러리 도입 시 신중*.
298
+
299
+ ### 13. `BlackjackEngine.cardDeck` 직접 생성 — *테스트 가능성 손상*
300
+
301
+ ```kotlin
302
+ class BlackjackEngine {
303
+ val cardDeck: CardDeck = CardDeck() // ⚠ 멤버 직접 생성
304
+ ...
305
+ }
306
+ ```
307
+
308
+ 말리빈 (BlackjackEngine.kt:4 — 미해결): *"카드 덱도 주입 받게끔 만들어야 테스트 코드를 작성하기 원활해지겠어요 :)"*
309
+
310
+ → **CardDeck은 ShuffleStrategy를 주입 가능**한데, `BlackjackEngine` 단계에서 다시 `CardDeck()` 으로 lock. *Engine 테스트 시 순서 고정 카드 시퀀스 주입 불가*. *생성자 인자*로 받는 *DI 패턴*이 자연. PR #112·#28·#125·#10 (Singleton Deck) 와 *부분적으로 같은 결* — *Engine이 Deck을 *직접 만든다*는 면이 *Singleton 의 변형*.
311
+
312
+ ### 14. `Player`/`Dealer` *firstCard val 멤버* + *Participant 의 hand* — *초기/현재 분리의 잔재*
313
+
314
+ ```kotlin
315
+ abstract class Participant(firstCard: List<Card>) {
316
+ val hand: Hand = Hand(firstCard)
317
+ ...
318
+ }
319
+
320
+ class Player(val name: String, val firstCard: List<Card>) : Participant(firstCard)
321
+ class Dealer(val firstCard: List<Card>, val name: String = DEALER_NAME) : Participant(firstCard) {
322
+ fun getAdditionalDrawCount(): Int = hand.getHandCount() - firstCard.size
323
+ ...
324
+ }
325
+ ```
326
+
327
+ → **`firstCard` 멤버 보유 + 생성자 인자 양쪽**. *Participant 생성자가 `firstCard` 받음 → Hand 생성 → 끝* 이어야 하는데 *Player/Dealer 도 `val firstCard`* 로 *영구 보유*. *Hand 안에 들어간 카드*와 *firstCard 멤버*가 *같은 List 참조* 인지 *별도 사본* 인지 명시 안 됨. `Hand(firstCard).toMutableList()` 가 *복사본*을 만드니 두 곳이 분리되어 있어 *하나만 변하면 분기*. *시간에 따라 다른 정보를 두 변수로 보유*하는 *시간 일관성 문제*.
328
+
329
+ *Dealer.getAdditionalDrawCount* 가 이 *시간 비교*의 사용처. *추가 뽑은 수* 자체가 *블랙잭 도메인 메시지가 아니라 출력용 카운터* (말리빈 *"콘솔 영향"* 진단과 정합). PR #124 (모찌) 의 `Dealer._results` 와 같은 결.
330
+
331
+ ### 15. `Players` *MAX_PLAYER_COUNT = 7* — *현실 카지노 기준?*
332
+
333
+ ```kotlin
334
+ class Players(val value: List<Player>) {
335
+ init {
336
+ require(value.size in MIN_PLAYER_COUNT..MAX_PLAYER_COUNT) { ... }
337
+ require(value.distinct().size == value.size) { ... }
338
+ }
339
+ companion object {
340
+ private const val MIN_PLAYER_COUNT = 1
341
+ private const val MAX_PLAYER_COUNT = 7
342
+ }
343
+ }
344
+ ```
345
+
346
+ 학생 PR 코멘트: *"플레이어가 8명까지 가능하고, 6덱을 넣었는데도 불구하고 카드가 모자라는 상황은 논리 오류라고 판단"*
347
+
348
+ → **현재 코드는 7명 제한 (8명 가정과 불일치 — PR 작성 후 다른 곳 수정한 흔적)**. *카지노 기준 = 6~7명*이 표준. *학생이 8명 가정* 했는데 *코드는 7* — *주석/PR 본문과 코드 어휘 불일치* 의 흔적. 안티패턴은 아니나 *도메인 가정 명시 부재*.
349
+
350
+ ### 16. `Card.SINGLE_DECK` companion val — *덱이 카드의 정적 데이터?*
351
+
352
+ ```kotlin
353
+ class Card(val rank: CardRank, val suit: CardSuit) {
354
+ companion object {
355
+ val SINGLE_DECK = CardRank.entries.flatMap { rank ->
356
+ CardSuit.entries.map { suit -> Card(rank, suit) }
357
+ }
358
+ ...
359
+ }
360
+ }
361
+ ```
362
+
363
+ → **`Card.SINGLE_DECK` 의 위치 모순** — *덱 = 52장 카드 모음*은 *`CardDeck` 도메인 책임*. *`Card.SINGLE_DECK`* 은 *Card 클래스가 덱을 알고 있음*. 의도는 *invoke 팩토리 캐시*. 다만 *Card 가 자기 종류만 알고 / Deck 이 52장 구성 책임*이 자연. *`Card` companion 의 캐시*는 `Map<(rank,suit), Card>` 가 더 적합. *`CardDeck.SINGLE_DECK`* 으로 이동 + *`Card` 팩토리는 캐시 lookup*. 현재는 *순환 의존 신호* — `CardDeck` 이 `Card.SINGLE_DECK` 을 import 하고 `Card` 가 자기 자신의 모든 인스턴스를 안다.
364
+
365
+ ### 17. `Dealer.drawUntilFinished` — *while + score + isBust 이중 조건*
366
+
367
+ ```kotlin
368
+ fun drawUntilFinished(cardDeck: CardDeck) {
369
+ while (hand.score() <= DEALER_DRAW_CRITERIA && !hand.isBust()) {
370
+ draw(cardDeck)
371
+ }
372
+ }
373
+ ```
374
+
375
+ → **`hand.score() <= 16 && !hand.isBust()`**. *`isBust` 면 score == -1* 이므로 *-1 <= 16 = true*. *isBust 명시*로 *센티넬 -1 트릭이 새는 것* 방지. *Hand 가 isBust 시 score = -1* 트릭이 *호출자에 새지 않도록* *호출자가 isBust 먼저* 확인하는 *방어 코드*. *센티넬 트릭의 비용*. *Hand.canDraw(): Boolean = score < 17 && !isBust()* 면 한 줄. PR #112 의 *상태 메시지 응집* 결과와 같은 결.
376
+
377
+ 또한 *`DEALER_DRAW_CRITERIA = 16`* 매직 넘버를 *Dealer companion* 에 두는 게 *카지노 룰 명세 위치* 로 적절한지는 의문. *블랙잭 룰 전체*가 *Dealer companion* 에 묻혀 있으면 *룰 조회*가 *Dealer 안 봐야 함*. *Rule/BlackjackRule* 같은 *룰 객체* 로 분리도 후보.
378
+
379
+ ### 18. `assertAll` — *그룹 어설션 학습 질문*
380
+
381
+ ```kotlin
382
+ // DealerTest.kt:60 — 추정
383
+ @Test
384
+ fun ...() {
385
+ assertEquals(...)
386
+ assertEquals(...)
387
+ assertEquals(...)
388
+ }
389
+ ```
390
+
391
+ 말리빈 (DealerTest.kt:60 — 미해결): *"assertAll 로 묶는 것과 그렇지 않은 것은 어떤 차이가 있을까요?"*
392
+
393
+ → **JUnit `assertAll` = 여러 어설션 묶어 모두 실행**. *하나 실패해도 나머지 어설션도 실행*하여 *전체 실패 정보 보고*. *기본 `assertEquals` 연속*은 *첫 실패에서 멈춤* → *다른 어설션의 통과/실패 정보 손실*. *테스트 진단 가시성* 학습.
394
+
395
+ ### 19. *`Hand` 의 `getHandCount` / `getScore` — getXXX 명사형*
396
+
397
+ ```kotlin
398
+ fun getHandCount(): Int = cards.size
399
+ fun score(): Int { ... }
400
+
401
+ // Participant
402
+ fun getHandSize(): Int = hand.getHandCount()
403
+ fun getScore(): Int = hand.score()
404
+ ```
405
+
406
+ 말리빈 (BlackjackEngine.kt:13 — 동사 시작 권고): *"메서드명은 동사로 시작하도록 작성해보세요 :)"*
407
+
408
+ → **`getXXX` 메서드명 = Java Bean 어휘**. *Kotlin은 `val handCount: Int get() = cards.size`* 같은 *property 문법*이 자연. `getXXX()` 함수형 호출은 *property로 노출* 하거나 *동사형 (`count()`, `scoreHand()`)*. *Kotlin 어휘 정착*. PR #28·#10·#119 와 같은 결 (`getXXX` 명사형 → Kotlin property 권고).
409
+
410
+ 또한 *`getScore()` 가 Hand 의 `score()` 를 그대로 위임*하고 *`Hand.score`는 함수 / Hand.cards 는 property* 로 *어휘 불일치*. *통일* 필요.
411
+
412
+ ## 리뷰어 의견 요지
413
+
414
+ - **invoke 팩토리 + class 생성자 = 호출 모호** — `Card(rank, suit)`가 어느 쪽인지 *바이트코드 안 보면 모름*. *private constructor + companion factory* 가 정공.
415
+ - **딜러는 왜 이름을 안 가지는가? = 변경 취약성 + 코드 탐색 위치** — 학생의 4 옵션 자가 토론에 대해 말리빈이 *"딜러 이름이 김딜러씨로 바뀌면 어떤게 가장 변경점에 취약? 이름은 어디에 있어야 자연? 다른 개발자가 딜러 이름을 어디서 찾을까?"* 메타 질문으로 *학생 자가 결론* 유도. *객체의 이름은 객체 안에* — *코드 탐색 위치 = 의미 위치*.
416
+ - **카드 부족 = 게임 종료는 비현실** — *카지노 = 무한 게임 가능*. *6덱이 다 떨어져도 새 카드 가져옴*. 학생의 *"6덱 + 8명이면 카드 모자라는 게 논리 오류"* 멘탈을 *"카지노 = 6시간 게임"* 으로 전환.
417
+ - **abstract = "고장 난 부분 채우라"** — *abstract method 0* 인 *Participant* 는 *abstract 키워드 의미 모호*. *open class + sealed class + interface property* 중 의도에 맞는 것 선택. *`abstract class` ≠ "추상 개념 표현"*.
418
+ - **싱글톤 Deck = 테스트 불가** — `object` 또는 *멤버 직접 생성*이 *순서 고정 카드 시퀀스 주입 불가*. *전략 패턴 + 생성자 주입* 으로 *셔플 추상화* (시아가 1단계 안에 자가 반영).
419
+ - **점수 직접 비교 = 블랙잭 룰 무지** — *21 초과 패배*, *2장 21 = 블랙잭*, *Bust 양측 무조건 패배* 모두 *점수 크기 비교*로 안 잡힘. *도메인 룰 학습 → 코드 반영*.
420
+ - **메시지 던지기 ≠ object 분리** — 학생이 *함수를 object로 옮긴 것*을 *"메시지 던지기"*라 자가 칭찬했지만 *진짜 메시지*는 *`participant.compete(other)`*. *`CalculateResult.getResult(a, b)` = 정적 헬퍼 = Ask*.
421
+ - **Inferred Type 리턴 = API 안전성 손상** — *외부 API*에서 *반환 타입 추론*은 *호출자가 타입 추론 어려움*. *Effective Kotlin Item 4·14*.
422
+ - **Kotlin stdlib 우선 = 멀티플랫폼 이식성** — *Java import*는 *JVM 결합*. *Kotlin은 JVM 외 플랫폼*도 타겟.
423
+ - **getXXX 명사형 → Kotlin property** — *Java Bean 어휘*를 *Kotlin property*로 정착.
424
+ - **반환 Int 의미 부재 = 콘솔 영향 흔적** — *몇 장 뽑았는지 Int 반환*은 *콘솔 출력용 카운터*. *도메인 메시지가 아닌 출력 카운터*는 *도메인에 누수*.
425
+ - **메서드명 길어도 의미 = 짧은 모호함 > 긴 명확함** — 말리빈 자가 예시: *`ObserveMyPermissionChangesOnSocketReconnectionUseCase`*.
426
+
427
+ ## 대표 인용
428
+
429
+ **말리빈 (abstract = "고장 난 부분", Participant.kt:5):**
430
+ > 생성자 로직을 포함할 수 없는 것은 공감이돼요.
431
+ > 그런데 참가자가 모두 자신의 핸드를 가지고 있기 때문에 한계가 명확한 것은 공감이 되지 않아요.
432
+ > 인터페이스에서 hand를 반드시 구현해야한다는 것을 명시하면 모두 Hand를 가지게 만들 수 있으니까요.
433
+ >
434
+ > abstract class는 고장 난 부분은 당신이 채워 넣으라 라는 의미에 가깝다고 생각해요.
435
+ > 그런데 여기에는 abstract할 게 하나도 없으니, abstract를 사용할 이유가 없다고 생각해요.
436
+
437
+ **말리빈 (메시지 던지기, WinningResult.kt):**
438
+ > 객체의 값을 직접 꺼내 비교하기보다, 객체에게 메시지를 던져보는 건 어떨까요?
439
+ > 그러다보면 이 점수 계산 로직이 어떠한 객체로 응집시킬 수 있어보이네요.
440
+
441
+ **말리빈 (이름은 어디에, Dealer.kt):**
442
+ > 딜러의 이름이 "김딜러씨"로 바뀌게 된다면 어떤게 가장 변경점에 취약할까요?
443
+ > 또 이름은 어디에 가지고 있어야 가장 자연스러울까요?
444
+ > 다른 개발자들이 딜러의 이름을 찾을 때 어떤 파일에 가서 찾아볼 것 같으신가요?
445
+
446
+ **말리빈 (카지노 = 무한 게임, CardDeck.kt):**
447
+ > 글쎄요.. 현실 세계에서도, 실제로 게임을 온라인으로 즐길 플레이어도,
448
+ > 몇 시간을 앉아서 게임하는 것은 흔히 볼 수 있는 광경이라 생각해요.
449
+ > 한 라운드가 돌았다 해서 항상 새 카드를 뜯어 쓰는 것도 아니구요.
450
+ >
451
+ > 카지노에서 덱 6벌이 사라졌으니, 카지노 문 닫고 손님들을 모두 쫓아내지 않는 것 처럼,
452
+ > 게임이 강제 종료되는 것은 문제라고 생각해요.
453
+
454
+ **말리빈 (invoke vs constructor 모호, Card.kt:18):**
455
+ > 이것은 생성자로 호출한 것인지 invoke 함수를 호출한 것인지 저도 모르겠는데요?
456
+ > Java의 바이트코드를 뜯어보지 않는 이상 어떤 것을 호출했는지 알기가 매우 어려워요.
457
+ > 생성자를 호출하는 케이스가 된다면, 중복된 값을 가지는 인스턴스를 생성할 수 있는 단점이 여전히 있겠어요.
458
+
459
+ **말리빈 (느슨한 결합, Controller):**
460
+ > 뷰와 모델을 결합하라는 의미가 아니에요.
461
+ > 느슨한 결합이라는 단어에 무언가 관점을 돌리기 어려워진 것 같네요.
462
+ > 결국 값을 전달한다는 것은 어떤 연결로 결합되어있기에 가능한것이겠지요.
463
+ > 이 결합은 완전히 서로를 아는 강한 결합일 수도 있고, 서로를 모른채 어떤 값을 주고 받을 수는 있는 약한 결합이 있을 수도 있겠지요.
464
+ > 도메인에서 필요한 값을 interface 혹은 람다 등으로 가져올 수 있도록 만들어보세요.
465
+ > **컨트롤러라는 이름 때문에 게임을 컨트롤 하는 기능을 컨트롤러에서 해야한다고 생각하는 건 아닐까 하는 생각도 문득 드네요.**
466
+
467
+ **말리빈 (긴 이름이 모호한 이름보다 낫다):**
468
+ > 이름이 길어지는 건 그게 무엇인지 알 길이 없어지는 것 보다 훨씬 낫다고 생각해요.
469
+ > 대충 회사에서 쓰고 있는 긴 변수명을 찾아보니 `ObserveMyPermissionChangesOnSocketReconnectionUseCase` 이런 것도 있네요.
470
+
471
+ **학생 자가 답변 (블랙잭 룰 자가 학습, WinningResult.kt):**
472
+ > 블랙잭 게임이 왜 블랙잭인가 했는데, 2장만으로 21점이 나오면 블랙잭이라 하는 걸 알게 되었습니다. 해당 사항에 맞게 수정하였습니다.
473
+
474
+ **학생 자가 답변 (딜러 이름 위치, Dealer.kt):**
475
+ > 이름이 없는 경우 딜러라고 출력하는 것이 더 여러 곳을 손보게 되겠네요.
476
+ > 거기에 개발자들도 객체의 이름을 객체 안에서 찾으려 할테니, 딜러의 이름은 딜러가 가지고 있는게 맞을 것 같습니다!
477
+
478
+ **학생 자가 답변 (object 분리를 메시지로 오해, CalculateResult.kt):**
479
+ > 로직을 분리하여 object로 만들었습니다! 메세지를 던지니 훨씬 더 객체끼리의 결합이 사는 듯 한 느낌이 드네요.
480
+
481
+ **학생 자가 답변 (Effective Kotlin 정리 후 자가 의문, BlackjackEngine.kt):**
482
+ > 먼저 생각한 것 -> 리턴타입을 명시하면 확실하게 리턴 타입이 보장되고, = 를 사용해서 리턴하면 코드 길이가 짧아지고 유연하게 작성할 수 있다.
483
+ > 책을 읽고 정리한 것 -> 외부 API에서 Inferred Type로 리턴하게 되면, API의 안전이 보장되지 않고, 개발자가 타입을 쉽게 추론할 수 없게 된다. 또한 명확하지 않은 변수 타입은 코드 가독성을 떨어트려 효율을 저하시킨다.
484
+ > 생각보다 리턴 타입이 보장되는 것이 정말 중요하네요, 코드를 짜면서 다른 개발자가 사용하는 경우를 거의 생각하지 않고 짜다 보니, 내가 알고 있으면 상관 없다고 생각했는데, API의 안전에도 영향을 끼칠 수 있다는 것을 알게 되었습니다.
485
+
486
+ ## 얻은 교훈
487
+
488
+ 1. ***`abstract class` 는 "추상 개념 표현 도구"가 아니라 "abstract method 채우기 강제 도구"***. *abstract method 0 + open property 0* 인 클래스에 *`abstract` 키워드*는 *의미 부재*. *인스턴스화 막기 = `sealed class` 또는 protected constructor*, *공통 상태/메서드 공유 = open class*, *공통 메서드 시그니처 강제 = interface*. *학생의 "abstract = 추상 개념 표현"* 사고가 *`abstract` 의 의미를 키워드 이름의 일상어 의미*로 해석한 결과. PR #28·#135·#114·#125 와 같은 결.
489
+
490
+ 2. ***메시지 던지기 = `participant.compete(other)`, 정적 헬퍼 분리가 아님***. 학생의 *"로직을 object로 분리 = 메시지 던지기"* 오해는 *`object` 가 싱글톤 = 정적 헬퍼 = Ask 패턴* 이라는 점을 놓침. *진짜 메시지* 는 *행위 주체에게 묻고 그 결과를 받음*. *Tell-Don't-Ask 의 핵심 = 호출자가 분기 안 만듦*.
491
+
492
+ 3. ***Java Bean 어휘 (`getXXX`/`setXXX`) → Kotlin property***. *`getHandCount()`* / *`getScore()`* 같은 *Java getter 형태*는 *Kotlin property* 로 정착. `val handSize: Int get() = hand.cards.size` 같은 *property 문법*이 *Kotlin 어휘*. *함수 vs property* 의 분기 기준: *부수효과 / 계산 비용 / 매번 다른 값* 이면 함수, *아니면 property*. PR #28·#10·#119 와 같은 결.
493
+
494
+ 4. ***카지노 = 무한 게임 메타포***. *카드 부족 → 게임 종료* 는 *현실 카지노 metaphor* 와 충돌. *6덱 다 떨어지면 새 6덱* 이 *현실*. 학생이 *"논리 오류"* 라 한 판단을 *말리빈이 "현실 = 6시간 게임"* 메타포로 전환. *현실 metaphor 자체*가 *코드 invariant 결정 기준*. PR #29·#34·#51 와 같은 결 (*현실 메타포 정합* 후속 학습).
495
+
496
+ 5. ***`invoke` 팩토리 + `public class` = 호출 모호. 팩토리 정공은 `private constructor` + `companion object fun of(...)`***. *Kotlin operator fun invoke 의 함정* — *같은 시그니처의 생성자가 우선*. *팩토리 메서드 패턴* 의 안전한 표현은 *생성자 private + 명명된 팩토리 함수*. PR #28·#125 와 같은 결.
497
+
498
+ 6. ***`firstCard` 멤버 보유 = 초기 상태와 현재 상태를 두 변수로 보관 = 시간 일관성 깨짐***. *생성자 인자만 받고 잊어버림*이 자연. *Dealer.getAdditionalDrawCount = hand.size - firstCard.size* 같은 *시간 비교*는 *출력용 카운터*이지 *도메인 메시지 아님*. 말리빈의 *"콘솔의 영향으로 이렇게 구성했다는 느낌이 강하게 드네요"* 진단이 *출력 위주 사고*의 도메인 누수 진단.
499
+
500
+ 7. ***메서드명은 동사로 시작 + Kotlin 어휘***. `playerDraw(player)` / `dealerDraw(dealer)` 는 *명사+동사 합성*. `drawForPlayer(player)` / *Player 자신이 draw* 가 자연. *어휘 일관성*.
501
+
502
+ 8. ***긴 이름이 모호한 이름보다 낫다***. 말리빈의 *`ObserveMyPermissionChangesOnSocketReconnectionUseCase`* 예시가 *극단적이지만 원칙*. *짧고 모호한 메서드명*보다 *길고 명확한 메서드명*. *IDE 자동완성 시대*에 *입력 비용은 0*. *읽는 비용은 매번*.
503
+
504
+ 9. ***Bust 점수를 센티넬(-1) + maxOf 트릭 < Ace 1 기본 + 단일 +10***. *학생의 트릭 (`baseScore.formatIfBust()` + `maxScoreWithAce(...).formatIfBust()` + `maxOf`)* 는 *작동은 함* 이지만 *복잡도 ↑ + isBust invariant 가 score==-1 에 묶임 + 호출자가 isBust 먼저 확인 강제*. *Ace 1 기본 + sum 계산 + Ace 있고 sum+10≤21 이면 +10* 패턴이 *한 줄*. PR #128·#135·#114·#125·#124 와 같은 결 (Ace 안티패턴 변형).
505
+
506
+ 10. ***Kotlin Multiplatform 관점 = Java import 자제***. *`java.util.Random` / `Collections.shuffle`* 같은 *Java 의존성*은 *Kotlin/JS, Kotlin/Native 이식 시 충돌*. *Kotlin stdlib (`shuffled()`, `random()`)* 이 *멀티플랫폼 안전*. *프로젝트가 JVM 한정*이라도 *습관*이 *향후 멀티플랫폼 도입 시 비용 절감*.
507
+
508
+ 11. ***학생의 *자가 의문 → 자가 답변 → 후속 자가 의문* 패턴이 학습 모범***. 시아의 *Effective Kotlin Item 4/14 → 본인 정리 → 자가 답변 → "Unit 타입은 어떻게?" 자가 의문 → 말리빈 보강* 흐름은 *수동적 적용*이 아니라 *능동적 학습*. *책 정리 시점에 자가 의문*이 *외부 학습 자료 활용의 정공*. PR #128·#135·#111·#120·#124 와 같은 결.
509
+
510
+ 12. ***결과 집계는 한 곳 — `Match/Game` 객체나 `GameResults` 일급 컬렉션***. *Dealer.getWinDrawLossResult(players)* + *Players.results(dealer)* 처럼 *결과 집계가 두 곳에 분산*하면 *두 결과의 일관성*을 *암묵적 invariant*로 보장해야 함. *한 객체가 매치를 진행하고 결과를 분배*가 자연.
511
+
512
+ 13. ***Engine 도입 자체는 좋으나 god-object 완전 해소가 아닐 수 있다***. *시아의 `BlackjackEngine`* 은 *Controller god-object* 의 일부 해소. 다만 *`cardDeck = CardDeck()` 멤버 직접 생성 + `playerDraw(player)`/`dealerDraw(dealer)` wrapper + Engine이 모든 진행을 흡수*. *Engine 자체가 god-object 의 이전된 형태*가 될 위험. *각 객체가 자기 책임* 흐름이 *Engine 거치는 wrapper*보다 메시지 패턴에 맞음. PR #112·#28 (BlackjackGame god-object) 와 같은 결.
513
+
514
+ 14. ***`Boolean` 반환 메시지 (`isBust`) 는 자기 점수 의미를 노출하지 않아야***. *`Hand.score()` 가 Bust 시 -1 반환* + *`isBust()` 가 score==-1 비교* 는 *Hand 내부 의미 (-1 센티넬) 가 호출자에 새는 함정*. *호출자가 `score()` 만 부르면 잘못된 정수*. *함수 분리* 면 *호출자가 안전*: `Hand.canCalculate(): Boolean` / `Hand.scoreOrNull(): Int?` / *throw + isBust* 등 다양.
515
+
516
+ 15. ***학생 자가 답변에 커밋 SHA 첨부 = 학습 가시화 모범 (Reviewer 친화)***. Leeyerin0210 이 *모든 후속 반영에 커밋 SHA*를 명시 (`141938f`, `a821755`, `29e4a32`, `0a2ae58`, `f62c66c`, `85b84de`, `558a794`, `fdc34e7`, `396235f`, `a94d03f`, `2fac65c`, `dfced9a`, `011cfff`, `13e5774` 등) → *말리빈이 "어디서 반영됐는지"* 즉시 확인 가능. PR #124 (모찌) 와 같은 결 (학생 자가 답변 + 커밋 SHA 첨부 패턴).