題目
求 1+2+...+n
,要求不能使用乘除法、for、while、if、else、switch、case等關鍵字及條件判斷語句(A?B:C)。
示例 1:
輸入: n = 3
輸出: 6
示例 2:
輸入: n = 9
輸出: 45
限制:
1 <= n <= 10000
解題思路
1)直接計算要使用運算符號,迭代要使用 while 或者 for 關鍵字,因此這兩個都不能使用。
2)再說遞歸,不能使用 if 關鍵字來終止遞歸,所以要考慮其他辦法終止遞歸,也就是邏輯運算符的短路性質。
常見的邏輯運算符有三種,即 “與 && ”,“或 || ”,“非 ! ”,而其有重要的短路效應:
if(A&&B) // 若 A 爲 false ,則 B 的判斷不會執行(即短路),直接判定 A&&B 爲false;
if(A||B) // 若 A 爲 true ,則 B 的判斷不會執行(即短路),直接判定 A||B 爲 true。
利用這一特性,我們可以將判斷是否爲遞歸的出口看作 A&&B 表達式中的 A 部分,遞歸的主體函數看作 B 部分。如果不是遞歸出口,則 A=true,並繼續執行表達式 B 的部分,否則遞歸結束。
本題需要實現 “當 n=1 時終止遞歸” 的需求,可通過上述的短路效應來實現:
n>1 && sumNums(n - 1) // 當 n = 1 時 n > 1 不成立 ,此時“短路”,終止後續遞歸;否則執行後半部分。
複雜度分析:
時間複雜度:O(n)。遞歸函數遞歸 n 次,每次遞歸中計算時間複雜度爲 O(1),因此總時間複雜度爲 O(n)。
空間複雜度:O(n)。遞歸函數的空間複雜度取決於遞歸調用棧的深度,這裏遞歸函數調用棧深度爲 O(n),因此空間複雜度爲 O(n)。
代碼
class Solution {
public int sumNums(int n) {
boolean flag = n > 1 && (n += sumNums(n-1))>0;
return n;
}
}