368. Largest Divisible Subset

  • Uniqueν•œ 숫자둜 이루어진 λ°°μ—΄ arr이 μ£Όμ–΄μ‘Œμ„ λ•Œ λ‹€μŒ 쑰건을 λ§Œμ‘±ν•˜λŠ” λΆ€λΆ„ 집합 쀑 κ°€μž₯ 크기가 큰 것을 κ΅¬ν•˜λŠ” 문제.
    • λΆ€λΆ„ μ§‘ν•©μ—μ„œ μž„μ˜μ˜ 2개 숫자 a, bλ₯Ό νƒν–ˆμ„ λ•Œ a % b == 0 λ˜λŠ” b % a == 0을 λ§Œμ‘±ν•œλ‹€.
  • 배열을 μ •λ ¬ν•˜μ—¬ ν’€μ–΄μ•Ό λœλ‹€λŠ” 것 κΉŒμ§€λŠ” μ•Œμ•˜λŠ”λ° λΆ€λΆ„ 집합을 κ΅¬μ„±ν•˜λŠ” 방식을 κ³ λ―Όν•˜λ‹€κ°€ 방법이 μƒκ°λ‚˜μ§€ μ•Šμ•„μ„œ 해닡을 λ³΄μ•˜λ‹€.
  • 배열을 μˆœνšŒν•˜λ©΄μ„œ ν˜„μž¬ 숫자λ₯Ό κΈ°μ€€μœΌλ‘œ 더 큰 λΆ€λΆ„ 집합을 κ΅¬μ„±ν•˜λŠ” 숫자λ₯Ό μ°Ύμ•„λ‚΄λŠ” λ°©μ‹μœΌλ‘œ ν’€μ–΄μ•Ό ν•œλ‹€.
    • λ¨Όμ € 배열을 μ˜€λ¦„μ°¨μˆœμœΌλ‘œ μ •λ ¬ν•œλ‹€.
    • 각 index λ³„λ‘œ λΆ€λΆ„ μ§‘ν•©μ˜ 크기 subsetSizeList와 ν˜„μž¬ 숫자의 λ°”λ‘œ 직전 μˆ«μžμ— λŒ€ν•œ index prevIndexListλ₯Ό κΈ°λ‘ν•œλ‹€.
    • ν˜„μž¬ 숫자 nums[i]λ₯Ό κΈ°μ€€μœΌλ‘œ μ•žμͺ½μ— μžˆλŠ” 숫자 nums[j] (j = 0, 1, …, i - 1) λ₯Ό μˆœνšŒν•˜λ©΄μ„œ 쑰건을 λ§Œμ‘±ν•˜λŠ” 숫자 nums[i] % nums[j] == 0 λ₯Ό μ°ΎλŠ”λ‹€.
    • 쑰건을 λ§Œμ‘±ν•˜λŠ” 숫자 쀑 λΆ€λΆ„ μ§‘ν•©μ˜ 크기가 κ°€μž₯ 크게 λ§Œλ“œλŠ” 숫자λ₯Ό μ„ νƒν•˜μ—¬ λΆ€λΆ„ μ§‘ν•©μ˜ 크기와 ν•΄λ‹Ή 숫자의 indexλ₯Ό κΈ°λ‘ν•œλ‹€.
    • λ§ˆμ§€λ§‰ index maxIndex 보닀 ν˜„μž¬ index의 λΆ€λΆ„ μ§‘ν•©μ˜ 크기가 더 크닀면 ν˜„μž¬ indexλ₯Ό λ§ˆμ§€λ§‰ index둜 ν•œλ‹€.
  • λ§ˆμ§€λ§‰ indexλΆ€ν„° 이전 index λ°°μ—΄ prevIndexList을 μˆœνšŒν•˜λ©΄μ„œ 전체 λΆ€λΆ„ 집합을 λ§Œλ“€μ–΄λ‚Έλ‹€.
class Solution { public List<Integer> largestDivisibleSubset(int[] nums) { Arrays.sort(nums); int n = nums.length; int[] subsetSizeList = new int[n]; int[] prevIndexList = new int[n]; int maxIndex = 0; for(int i = 0; i < n; ++i) { int subsetSize = 1; int prevIndex = -1; for(int j = 0; j < i; ++j) { if(nums[i] % nums[j] == 0) { int newSubsetSize = subsetSizeList[j] + 1; if(newSubsetSize > subsetSize) { subsetSize = newSubsetSize; prevIndex = j; } } } subsetSizeList[i] = subsetSize; prevIndexList[i] = prevIndex; if(subsetSize > subsetSizeList[maxIndex]) { maxIndex = i; } } List<Integer> result = new ArrayList(); for (int i = maxIndex; i != -1; i = prevIndexList[i]) { result.add(nums[i]); } return result; } }