[sangbeenmoon] WEEK 05 Solutions#2776
Conversation
📊 sangbeenmoon 님의 학습 현황이번 주 제출 문제
누적 학습 요약
문제 풀이 현황
🤖 이 댓글은 GitHub App을 통해 자동으로 작성되었습니다. 🔢 API 사용량 (gpt-5-nano)
|
There was a problem hiding this comment.
🏷️ 알고리즘 패턴 분석
- 패턴: Hash Map / Hash Set, Dynamic Programming
- 설명: 두 코드 모두 문자열을 정렬한 값을 키로 사용하여 그룹을 묶는 방식으로 해시맵(딕셔너리)을 활용합니다. 첫 번째는 방문 배열과 중복 판단으로 묶고, 두 번째는 해시 맵에 리스트를 누적합니다. 패턴은 해시 기반 그룹화에 해당합니다.
📊 시간/공간 복잡도 분석
| 복잡도 | |
|---|---|
| Time | O(n * k log k) |
| Space | O(n * k) |
피드백: 첫 번째 풀이와 두 번째 풀이 모두 각 문자열을 정렬한 키를 사용해 그룹을 구성한다. 해시맵으로 그룹을 모으는 방식은 효율적이며 두 번째 풀이에서 defaultdict/집합의 중복 복사를 다루는 부분이 비효율적일 수 있다.
개선 제안: 현재 구현이 적절해 보입니다.
💡 풀이에 시간/공간 복잡도를 주석으로 남겨보세요!
There was a problem hiding this comment.
🏷️ 알고리즘 패턴 분석
- 패턴: Trie
- 설명: 트라이 구조를 이용한 문자열 저장 및 검색 구현으로 패턴은 Trie입니다. insert, search, startsWith를 재귀적으로 노드를 따라가며 동작합니다.
📊 시간/공간 복잡도 분석
ℹ️ 이 파일에는 4가지 풀이가 포함되어 있어 각각 분석합니다.
풀이 1: Trie.insert — Time: O(L) / Space: O(Total characters)
| 복잡도 | |
|---|---|
| Time | O(L) |
| Space | O(Total characters) |
피드백: 재귀적으로 자식 노드를 따라가고 새 노드를 생성하는 방식으로 삽입이 진행된다.
개선 제안: 현재 구현이 적절해 보입니다.
풀이 2: Trie.search — Time: O(L) / Space: O(1)
| 복잡도 | |
|---|---|
| Time | O(L) |
| Space | O(1) |
피드백: 재귀적 검색으로 단어의 존재를 확인한다.
개선 제안: 현재 구현이 적절해 보입니다.
풀이 3: Trie.startsWith — Time: O(L) / Space: O(1)
| 복잡도 | |
|---|---|
| Time | O(L) |
| Space | O(1) |
피드백: 재귀적으로 접두사를 따라가며 존재 여부를 판단한다.
개선 제안: 현재 구현이 적절해 보입니다.
풀이 4: Trie — Time: O(1) / Space: O(1)
| 복잡도 | |
|---|---|
| Time | O(1) |
| Space | O(1) |
피드백: 루트 관리 및 메서드 위임으로 사용에 편리하다.
개선 제안: 현재 구현이 적절해 보입니다.
💡 풀이에 시간/공간 복잡도를 주석으로 남겨보세요!
There was a problem hiding this comment.
🏷️ 알고리즘 패턴 분석
- 패턴: Dynamic Programming, Backtracking, Hash Map / Hash Set
- 설명: 초기 풀이 부분은 재귀와 가지치기, 중복 방문 방지를 통해 가능 여부를 탐색하는 백트래킹 성격이다. 두 번째 부분은 DP를 이용한 메모이제이션으로 구간 시작 위치의 가능성을 기초로 결과를 도출한다. 또한 사전 형태로 단어를 빠르게 확인하기 위해 해시 맵을 사용한다.
📊 시간/공간 복잡도 분석
| 복잡도 | |
|---|---|
| Time | O(n^2) |
| Space | O(n) |
피드백: 초기 실패한 풀이와 달리 dp를 활용해 중복 계산을 제거하려는 시도가 보인다.
개선 제안: 현재 구현이 적절해 보입니다.
💡 풀이에 시간/공간 복잡도를 주석으로 남겨보세요!
| if sorted_target in d: | ||
| group = d[sorted_target] | ||
| group.append(target) | ||
| d[sorted_target] = group.copy() | ||
| else: | ||
| group = [target] | ||
| d[sorted_target] = group.copy() |
There was a problem hiding this comment.
if sorted_target in d:
d[sorted_target].append(target)
else:
d[sorted_target] = [target]
There was a problem hiding this comment.
이렇게 하시는게 훨씬 나을거에요, 지금 코드에서 copy는 의미를 모르겠어요
| for candidate in d.values(): | ||
| answer.append(candidate) | ||
|
|
||
| return answer |
There was a problem hiding this comment.
list(d.values())
이렇게 리스트로 형변환 하시면 answer 없이 바로 가능하세요
| class TrieNode: | ||
|
|
||
| def __init__(self): | ||
| self.d = {} |
| class Solution: | ||
| def wordBreak(self, s: str, wordDict: List[str]) -> bool: | ||
|
|
||
| d = {} |
There was a problem hiding this comment.
의미에 맞는 네이밍을 해주시면 좋을 거 같습니다.
| d[sorted_target] = group.copy() | ||
| else: | ||
| group = [target] | ||
| d[sorted_target] = group.copy() |
| node.insert(word[1:]) | ||
|
|
||
| def search(self, word): | ||
| if word == "": | ||
| return self.is_end | ||
|
|
||
| target = word[0] | ||
|
|
||
| if target in self.d: | ||
| return self.d[target].search(word[1:]) |
There was a problem hiding this comment.
[1:]이 O(n)이라 현재 insert, search에서 탐색 성능이 좋지 않은 거 같습니다. [1:]을 사용하지 않고 구현해보시면 좋을 거 같습니다.
| class Trie: | ||
|
|
||
| def __init__(self): | ||
| self.root = TrieNode() | ||
|
|
||
| def insert(self, word: str) -> None: | ||
| self.root.insert(word) | ||
|
|
||
| def search(self, word: str) -> bool: | ||
| return self.root.search(word) | ||
|
|
||
| def startsWith(self, prefix: str) -> bool: | ||
| return self.root.startsWith(prefix) |
There was a problem hiding this comment.
Trie에는 구현이 없고 TrieNode에 모든 구현을 하신 이유가 있을까요?
답안 제출 문제
작성자 체크 리스트
In Review로 설정해주세요.검토자 체크 리스트
Important
본인 답안 제출 뿐만 아니라 다른 분 PR 하나 이상을 반드시 검토를 해주셔야 합니다!