旋轉字串

OrangeCat_發表於2018-09-30

描述

給定一個字串和一個偏移量,根據偏移量偏移字串(從左向右偏移)

樣例

對於字串 "abcdefg".

offset=0 => "abcdefg"
offset=1 => "gabcdef"
offset=2 => "fgabcde"
offset=3 => "efgabcd"

挑戰

在陣列上原地旋轉,使用O(1)的額外空間


解題思路

首先從在一個巨集觀的角度來看,偏移會把後幾個字元移動到整個字串的開頭,比如"offset=1 => "gabcdef" 會把 移動到字串的開頭,"offset=3 => "efgabcd"會把 efg 移動到字串的開頭。這樣來看,有點類似於反轉陣列。所以我們先反轉整個字串。

// 原字串
str = "abcdefg"

// 反轉後
str = "gfedcba"

 

但是在反轉後,字元的順序出現了變化,變成了區域性逆序的陣列了,因此我們需要對原先的後幾個字元和前幾個字元分別再做一個逆序。

// 假設offset = 3, 原字元
str = "abcdefg"

// 反轉後
str = "gfedcba"

// 對前3個字元再做一個逆序
str = "efgdcba"

// 對後4個字元再做一次逆序
str + "efgabcd"


原始碼

public class Solution
{
    public static void rotateString(char[] str, int offset)
    {
        if(str == null || str.length == 0 || offset % str.length == 0)
            return;

        // 這裡考慮到offset 大於 str.length的情況
        // 例如str.length = 7 offset = 9
        // 實際上每個字元實際偏移的長度是2
        offset = offset % str.length;

        reverse(str, 0, str.length-1);        // 先對整個字串做反轉
        reverse(str, 0, offset-1);            // 對前幾個字元做區域性反轉
        reverse(str, offset, str.length-1);   // 對後幾個字元做區域性反轉
    }

    public static void reverse(char[] str, int start, int end)
    {
        for(int i = start, j = end; i < j; i++, j--)
        {
            char temp = str[i];
            str[i] = str[j];
            str[j] = temp;
        }
    }
}

 

相關文章