
https://leetcode.com/problems/longest-consecutive-sequence/description/
intํ nums ๋ฐฐ์ด์ด ์ ๋ ฌ๋์ง ์์ ์ฑ๋ก ์ฃผ์ด์ก์ ๋, ์ฐ์์ ์ธ ์์ ์ํ์ค์ ๊ธธ์ด๋ฅผ ๋ฆฌํดํ๋ผ.(๋จ, O(N) ๋ด์ ๋ฐํ์์ ๊ตฌ์ฑํด์ผ ํ๋ค. -> sort ์ฐ์ง ๋ง๋ผ๋ ๋ป!)
๐ง์ ์ฝ ์กฐ๊ฑด
0 <= nums.length <= 10^5 => longest_length = 0์ผ๋ก ์ด๊ธฐํํ๋ผ๋ ๋ป
-10^9 <= nums[i] <= 10^9 => ์ต์๊ฐ์ ์ฐพ์ผ์์ค
containsKey()๋ก ๊ฒ์ฌํด์ ์ํ์ค๋ฅผ ๋ฝ์๋ผ ์ ์์Math.min() ๋ฉ์๋๋ฅผ ์ฌ์ฉํด์ ์ต์๊ฐ์ ์
๋ฐ์ดํธํ๋ค.map.containsKey(min_val)์ด ์ฐธ์ด๋ฉด map์ ์๋ ๊ธฐ์กด์ min_val์ ์ ๊ฑฐํ๊ณ min_val์ 1์ฉ ์ฆ๊ฐ์์ผ์ key chaining์ ์ฌ์ฉํด์ sequence๋ฅผ ๋ฝ์๋ธ๋ค.public class LcsSolution {
public int longestConsecutive(int[] nums) {
HashMap<Integer, Boolean> map = new HashMap<>();
List<Integer> keyStack = new ArrayList<>();
int longest_length = 0; // due to zero of nums.length
int min_val = Integer.MAX_VALUE;
// nums์ ๊ธธ์ด๊ฐ 0์ด๋ฉด ๊ทธ๋๋ก ๋ฆฌํด
if (nums.length == 0) {
return longest_length;
}
// ๋ฐฐ์ด -> Set(์ค๋ณต๋๋ ์์ ์ ๊ฑฐํ๊ธฐ ์ํจ)
Set<Integer> numSet = Arrays.stream(nums)
.boxed() // int -> Integer
.collect(Collectors.toSet());
// ๋จผ์ nums[i]๋ฅผ ๋ชจ๋ ์ ์ฅ && ์ต์๊ฐ ์ค์
for (int i : numSet) {
map.put(i, true);
min_val = Math.min(i, min_val);
}
for (int i = 0; i < map.size(); i++) {
if (map.isEmpty()) {
break;
}
while (map.containsKey(min_val)) {
map.remove(min_val); // for key chaining
min_val += 1;
longest_length += 1; // for return consecutive length
}
keyStack.add(longest_length);
longest_length = 0; // ๋ค์ 0์ผ๋ก ์ด๊ธฐํ
//! ๋๊ฐ์ด ์ธ๋ถ ๋ฃจํ ๋ด์์ ๋ฐ๋ณตํ๊ธฐ ๋๋ฌธ์ ์ต์ข
์ ์ผ๋ก O(N^2)์ด ๊ฑธ๋ฆผ
min_val = Integer.MAX_VALUE;
for (Integer key : map.keySet()) {
if (key < min_val) {
min_val = key;
}
}
}
// longest_length ์ต๋๊ฐ์ ๋ฆฌํด
int max_val = Integer.MIN_VALUE;
for (int num : keyStack) {
max_val = Math.max(num, max_val);
}
return max_val;
}
}
๐ฉ์ด ์ฝ๋์ ๋ฌธ์ ์ ์ ์ธ๋ถ ๋ฃจํ ๋ด์์ ์ต์๊ฐ์ ์ฐพ๊ธฐ ์ํด map.keySet()์ ์ํํ๋ ๋ถ๋ถ์ธ๋ฐ, ์ด ์์
์ด ์ธ๋ถ ๋ฃจํ๊ฐ ๋ฐ๋ณต๋ ๋๋ง๋ค ์ํ๋์ด O(nยฒ) ์๊ฐ ๋ณต์ก๋๊ฐ ๋ฐ์ํ๋ค๋ ๊ฒ์ด๋ค.
๐กwhile (map.containsKey(min_val))์ key๋ฅผ ํ์ํ๋๋ฐ O(1)๋ง ๊ฑธ๋ฆฌ๊ธฐ ๋๋ฌธ์ ๋ฌธ์ ๊ฐ ๋์ง ์๋๋ค.
๐ต2์๊ฐ ์ด์ ๊ณ ๋ฏผํด๋ ๋ต์ ๋ชป์ฐพ์์ AI์ ๋์์ ๋ฐ์๋ค.
๐nums์์ ์ํ์ค๋ฅผ ์ฐพ๊ธฐ ์ํ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ด ํ์
๐ค์ฝ๋ ์ค๊ณ๋ ๋ค์๊ณผ ๊ฐ์ต๋๋ค:
1. ์ํ์ค์ ์์์ ๋ง ์ฒ๋ฆฌํฉ๋๋ค(num-1์ด ์๋ ์ซ์).
2. ์์์ ์ ์ฐพ์ผ๋ฉด, ํด๋น ์ง์ ๋ถํฐ ์ฐ์๋ ์ซ์๋ฅผ ์ฐพ์ ์ํ์ค ๊ธธ์ด๋ฅผ ๊ณ์ฐํฉ๋๋ค.
public class LcsSolution {
public int longestConsecutive(int[] nums) {
HashSet<Integer> set = new HashSet<>();
int streak = 1; // longest_streak์ ์
๋ฐ์ดํธํ๊ธฐ ์ํด ์ ์ญ๋ณ์ ์ค์
if (nums.length == 0) {
return 0;
}
for (int i : nums) {
set.add(i);
}
for (Integer num : set) {
if (!set.contains(num - 1)) {
int curNum = num; // ์ํ์ค ์์์ ์ผ๋ก ์ค์
int curStreak = 1; // ๋ค๋ฅธ ์ํ์ค ๊ฒ์ฌ ์ํด ๋ค์ 1๋ก ์ค์
while (set.contains(curNum + 1)) {
curStreak += 1;
curNum += 1;
}
streak = Math.max(curStreak, streak); // ์ํ์ค ์
๋ฐ์ดํธ
}
}
return streak;
}
}
if (!set.contains(num - 1)) int curNum = num๋ก ์ฒ๋ฆฌํ์๋ค.while (set.contains(curNum + 1)) curNum += 1๋ก ์ฒ์์ ์ฝ๋ ๊ตฌํํ๋ key chaining๊ณผ ๋น์ทํ๊ฒ ๊ตฌํํ๊ณ , ์ฐ์๋ ์ซ์๋ฅผ ์ฐพ์ ๋๋ง๋ค curStreak += 1์ ํ์๋ค.๐ก์๋ฐ์์๋ for๋ฌธ, if๋ฌธ ๋ด์ ๋ธ๋ก์ผ๋ก ๋ณ์ ์ค์ฝํ๋ฅผ ์ ์ํ๊ธฐ ๋๋ฌธ์ streak๋ฅผ ์ ๋ฐ์ดํธ ํ๊ธฐ ์ํด ๋ฉ์๋ ๋ ๋ฒจ์์ streak๋ฅผ 1๋ก ์ด๊ธฐํํ์๋ค.
๐คfor๋ฌธ ๋ด๋ถ์ while๋ฌธ๋ N๋ฒ ๋ฐ๋ณตํ๋๊น ์ต์ข
์ ์ผ๋ก O(N^2)์ด ๊ฑธ๋ฆฌ์ง ์๋์?
๐์ฐ์๋ ์ซ์๋ฅผ ๋ฐ๋ผ๊ฐ๋ฉฐ ๊ฐ ์ซ์๋ฅผ ๋ฑ ํ ๋ฒ์ฉ๋ง ๋ฐฉ๋ฌธํ๊ณ , ๋ง์ฝ ๋ฐฉ๋ฌธ์ ํ๋ค๋ฉด if๋ฌธ์์ ๊ฑธ๋ฌ์ง๊ธฐ ๋๋ฌธ์ ์ต์ข
์ ์ผ๋ก for๋ฌธ์ ์์๋งํผ๋ง ์ํํด์ O(N)๋ง ๊ฑธ๋ฆฐ๋ค.
set.contains()ํจ์๋ O(1)๋ง ๊ฑธ๋ฆผ