1. 程式人生 > 其它 >[Leetcode學習-c++&java]Reach a Number

[Leetcode學習-c++&java]Reach a Number

技術標籤:JavaC++

問題:

難度:medium

說明:

假設你有一個無限座標軸,然後你 第 N 步 可以一次移動 N 個位置(從 1 開始),給出一個座標 T,求最少多少步可以移動到座標 T。

題目連線:https://leetcode.com/problems/reach-a-number/

輸入範圍:

  • targetwill be a non-zero integer in the range[-10^9, 10^9].

輸入案例:

Example 1:
Input: target = 3
Output: 2
Explanation:
On the first move we step from 0 to 1.
On the second step we step from 1 to 3.

Example 2:
Input: target = 2

Output: 3
Explanation:
On the first move we step from 0 to 1.
On the second move we step  from 1 to -1.
On the third move we step from -1 to 2.

我的程式碼:

數學題,如果用 bfs 肯定空間都爆了,畢竟是 空間佔用 指數增長。

1、

假設走 N 步到達,那麼其中有 K 步反著走是最短行程

假設輸入數字為 T,最少需要 N 步到達 T,如果 N 步都正向望著 T 走,那麼從 0 到 第 N 步長度為 SUM = N * (N + 1) <<1

那麼如果我其中第一步反著走,從 0 到 第 N 步長度為 SUM - (1 << 1),我第 K 步反著走就是SUM - (K<< 1)

那麼某幾步反著走就是SUM - ((K1 + K2 + K3 + .....) << 1) =SUM - (ΣK<< 1)

2、

把輸入負數都弄成正數,因為走路的邏輯一致。

SUM >= T,所以N * (N + 1) <<1 >= T

得出:N^2 + N - 2T >= 0 (一元二次方程)

根據一元二次方程求根得:(\sqrt{1 + 8T} - 1) / 2= N1 (N1必定是正數)

3、

從 N1 開始搜尋,因為 N1 開始才能獲得 SUM >= T

有 SUM - T = X = (K << 1),因為存在SUM - (K<< 1) =T

所以 K = SUM - T >> 1,如果 SUM - T 是奇數就跳過,不存在 SUM - T 為奇數

那麼第 N 步是到達 T的步數,只要有 N + N - 1 >= K 就肯定包含 K1 K2 K3 ...的一個集合,滿足 K = SUM - T(為什麼剛好 N + N - 1我忘了)

4、

所以比較爽的一道題可以用數學公式搞定

JAVA:

class Solution {
    public int reachNumber(int target) {
        long t = (long)Math.abs(target);
        int begin = (int)Math.ceil((Math.ceil(Math.sqrt(8 * t + 1)) - 1) / 2);
        for(int i = begin;;i ++) {
            int sum = (int)((i * (i + 1) >> 1) - t);
            if((sum & 1) == 0) {
                sum >>= 1;
                if(i + i - 1 >= sum) return i;
            }
        }
    }
}

C++:

class Solution {
public:
    int reachNumber(int target) {
        long t = (long)abs(target);
        int begin = (int)ceil((ceil(sqrt(8 * t + 1)) - 1) / 2);
        for(int i = begin;;i ++) {
            int sum = (int)((i * (i + 1) >> 1) - t);
            if((sum & 1) == 0) {
                sum >>= 1;
                if(i + i - 1 >= sum) return i;
            }
        }
    }
};