題目:算法
Implement next permutation, which rearranges numbers into the lexicographically next greater permutation of numbers.數組
If such arrangement is not possible, it must rearrange it as the lowest possible order (ie, sorted in ascending order).spa
The replacement must be in-place, do not allocate extra memory.設計
Here are some examples. Inputs are in the left-hand column and its corresponding outputs are in the right-hand column.1,2,3
→ 1,3,2
3,2,1
→ 1,2,3
1,1,5
→ 1,5,1
code
題意:blog
產生下一個序列,對給定序列進行重排,生成一個字母順序比它更大的下一個序列。it
若是給定的序列已是按字母順序排列中最大的一個了,則進行逆序排列。io
算法在數組內進行,不要使用額外空間。class
算法設計:遍歷
(1)從後向前遍歷,找到第一個不知足降序的元素;若初始序列所有是降序,則i爲-1,直接跳轉至(3);
(2)將該元素同它後面的元素中比它大的第一個元素交換;
(3)將該元素後的全部元素排列,使之成爲最小的排列。
代碼:
public void nextPermutation(int[] nums) { if(nums == null || nums.length == 0) return; //長度爲1的數組 if (nums.length == 1) { return; } //從後向前找到第一個不知足逆序的元素 int i = nums.length - 2; for(; i >= 0 && nums[i] >= nums[i + 1]; --i); //注意,這裏有=,能夠排除含有重複元素的狀況 //從i+1位置開始,向後查找比nums[i]大的最小元素 if(i >= 0){ int j = i + 1; for(; j < nums.length && nums[j] > nums[i]; ++j); swap(nums,i,j - 1); //交換,注意是同 j - 1交換 } //將i以後的元素逆置(這裏包含一種特殊狀況,若該排列已是字典序中的最大了,則下一個序列應該是最小字典序,所以,直接在這裏逆置便可) int k = nums.length - 1; i++; for(; i < k; i++, k--) swap(nums, i, k); } /** * 交換元素 * @param array * @param i * @param j */ public void swap(int[] array,int i ,int j){ //交換 int tmp = array[i]; array[i] = array[j]; array[j] = tmp; }