Skip to content

Commit

Permalink
[String] Add a solution to Find the Closest Palindrome
Browse files Browse the repository at this point in the history
  • Loading branch information
soapyigu committed Dec 1, 2019
1 parent 1189b4a commit 2af783b
Show file tree
Hide file tree
Showing 3 changed files with 76 additions and 2 deletions.
6 changes: 5 additions & 1 deletion DP/BestTimeBuySellStockIV.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,11 @@
return makeMaxProfit(prices)
}

var local = Array(repeating: 0, count: k + 1), global = Array(repeating: 0, count: k + 1)
// local[i] means the maxProfit when sell happens at ith day
var local = Array(repeating: 0, count: k + 1)

// global[i] means the maxProfit at ith day
var global = Array(repeating: 0, count: k + 1)

for i in 0..<n - 1 {
let diff = prices[i + 1] - prices[i]
Expand Down
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
![Leetcode](./logo.png?style=centerme)

## Progress
[Problem Status](#problem-status) shows the latest progress to all 1000+ questions. Currently we have 292 completed solutions. Note: questions with &hearts; mark means that you have to **Subscript to premium membership** of LeetCode to unlock them.
[Problem Status](#problem-status) shows the latest progress to all 1000+ questions. Currently we have 293 completed solutions. Note: questions with &hearts; mark means that you have to **Subscript to premium membership** of LeetCode to unlock them.

## Contributors

Expand Down Expand Up @@ -130,6 +130,7 @@
[Longest Substring with At Most Two Distinct Characters](https://leetcode.com/problems/longest-substring-with-at-most-two-distinct-characters/)| [Swift](./String/LongestSubstringMostTwoDistinctCharacters.swift)| Hard| O(n)| O(n)|
[Longest Substring with At Most K Distinct Characters](https://leetcode.com/problems/longest-substring-with-at-most-k-distinct-characters/)| [Swift](./String/LongestSubstringMostKDistinctCharacters.swift)| Hard| O(n)| O(n)|
[Text Justification](https://leetcode.com/problems/text-justification/)| [Swift](./String/TextJustification.swift)| Hard| O(n)| O(n)|
[Find the Closest Palindrome](https://leetcode.com/problems/find-the-closest-palindrome/)| [Swift](./String/FindClosestPalindrome.swift)| Hard| O(n)| O(n)|

## Linked List
| Title | Solution | Difficulty | Time | Space |
Expand Down
69 changes: 69 additions & 0 deletions String/FindClosestPalindrome.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
/**
* Question Link: https://leetcode.com/problems/find-the-closest-palindrome/
* Primary idea: Five possible cases -- the numbers with digits less or greater than current number;
* the numbers with same digits' number but replication of the mutation
* (+1 or -1 if the original number itself is palindrome) of the first half.
*
* Time Complexity: O(n), Space Complexity: O(1)
*
*/

class FindClosestPalindrome {
func nearestPalindromic(_ n: String) -> String {
let chars = Array(n)
var candidates = Set<String>()

candidates.insert(buildLeftNum(n))
candidates.insert(buildRightNum(n))

for distance in -1...1 {
candidates.insert(buildPalindromeOnMiddle(chars, distance))
}

return findNearest(n, candidates)
}

private func buildLeftNum(_ num: String) -> String {
return String(repeating: "9", count: num.count - 1)
}

private func buildRightNum(_ num: String) -> String {
return "1" + String(repeating: "0", count: num.count - 1) + "1"
}

private func buildPalindromeOnMiddle(_ n: [Character], _ distance: Int) -> String {
let middleIdx = n.count % 2 == 0 ? n.count / 2 - 1: n.count / 2
let leftPart = String(Int(String(n[0...middleIdx]))! + distance)

if n.count % 2 != 0 {
return String(leftPart.dropLast() + leftPart.reversed())
} else {
return String(leftPart + leftPart.reversed())
}
}

private func findNearest(_ n: String, _ candidates: Set<String>) -> String {
guard let num = Int(n) else {
fatalError("Invalid Input")
}

var nearest = 0

for candidate in candidates {
guard let cNum = Int(candidate) else {
continue
}
if cNum == num {
continue
}

if abs(cNum - num) < abs(nearest - num) {
nearest = cNum
} else if abs(cNum - num) == abs(nearest - num) {
nearest = min(cNum, nearest)
}
}

return String(nearest)
}
}

0 comments on commit 2af783b

Please sign in to comment.