[LeetCode] Additive Number
Af first I read the title as "Addictive Number". Anyway, this problem can be solved elegantly using recursion. This post shares a nice recursive C++ code with handling of the follow-up by implementing string addition function.
The code is rewritten as follows.
1 class Solution { 2 public: 3 bool isAdditiveNumber(string num) { 4 int n = num.size(); 5 for (int i = 1; i <= n/2; i++) 6 for (int j = 1; j <= (n-i)/2; j++) 7 if (additive(num.substr(0, i), num.substr(i, j), num.substr(i + j))) 8 return true; 9 return false; 10 } 11 private: 12 bool additive(string a, string b, string c) { 13 string s = add(a, b); 14 if (s == c) return true; 15 if (c.size() <= s.size() || s.compare(c.substr(0, s.size()))) 16 return false; 17 return additive(b, s, c.substr(s.size())); 18 } 19 string add(string& a, string& b) { 20 string s; 21 int i = a.size() - 1, j = b.size() - 1, c = 0; 22 while (i >= 0 || j >= 0) { 23 int d = (i >= 0 ? (a[i--] - '0') : 0) + (j >= 0 ? (b[j--] - '0') : 0) + c; 24 s += (d % 10 + '0'); 25 c = d / 10; 26 } 27 if (c) s += ('0' + c); 28 reverse(s.begin(), s.end()); 29 return s; 30 } 31 };
This problem can also be solved iteratively, like peisi's code, which is rewritten in C++ below.
1 class Solution { 2 public: 3 bool isAdditiveNumber(string num) { 4 int n = num.length(); 5 for (int i = 1; i <= n/2; i++) 6 for (int j = 1; max(i, j) <= n - i - j; j++) 7 if (additive(i, j, num)) return true; 8 return false; 9 } 10 private: 11 bool additive(int i, int j, string& num) { 12 if (num[i] == '0' && j > 1) return false; 13 string a = num.substr(0, i); 14 string b = num.substr(i, j); 15 for (int k = i + j; k < num.length(); k += b.length()) { 16 b.swap(a); 17 b = add(a, b); 18 string tail = num.substr(k); 19 if (b.compare(tail.substr(0, b.size()))) return false; 20 } 21 return true; 22 } 23 string add(string& a, string& b) { 24 string s; 25 int i = a.size() - 1, j = b.size() - 1, c = 0; 26 while (i >= 0 || j >= 0) { 27 int d = (i >= 0 ? (a[i--] - '0') : 0) + (j >= 0 ? (b[j--] - '0') : 0) + c; 28 s += (d % 10 + '0'); 29 c = d / 10; 30 } 31 if (c) s += ('0' + c); 32 reverse(s.begin(), s.end()); 33 return s; 34 } 35 };
If you are a Pythoner, you may also love Stefan's code, which is pasted below.
1 def isAdditiveNumber(self, num): 2 n = len(num) 3 for i, j in itertools.combinations(range(1, n), 2): 4 a, b = num[:i], num[i:j] 5 if b != str(int(b)): 6 continue 7 while j < n: 8 c = str(int(a) + int(b)) 9 if not num.startswith(c, j): 10 break 11 j += len(c) 12 a, b = b, c 13 if j == n: 14 return True 15 return False