题目描述:
LeetCode 386. Lexicographical Numbers
Given an integer n, return 1 - n in lexicographical order.
For example, given 13, return: [1,10,11,12,13,2,3,4,5,6,7,8,9].
Please optimize your algorithm to use less time and space. The input size may be as large as 5,000,000.
题目大意:
给定一个整数n,返回1到n的字典序排列。
例如,给定13,返回 [1,10,11,12,13,2,3,4,5,6,7,8,9]。
请优化你的算法,使用更少的时间与空间。输入规模可能会达到5,000,000。
解题思路:
解法I 递归(Recursive)构造法
优先将数字乘10;如果数字末位<9,考虑将数字加1
递归式类似于二叉树的先根遍历
伪代码如下:
def solve(m): result.append(m) if m * 10 <= n: solve(m * 10) if m < n and m % 10 < 9: solve(m + 1)
Java代码:
public class Solution {
private List<Integer> result;
private int n;
public List<Integer> lexicalOrder(int n) {
this.result = new ArrayList<Integer>();
this.n = n;
solve(1);
return result;
}
private void solve(int m) {
result.add(m);
if (m * 10 <= n) solve(m * 10);
if (m < n && m % 10 < 9) solve(m + 1);
}
}
由于递归的内存开销比较大,Python代码返回Memory Limit Exceeded
Python代码:
class Solution(object):
def lexicalOrder(self, n):
"""
:type n: int
:rtype: List[int]
"""
result = []
def solve(m):
result.append(m)
if m * 10 <= n: solve(m * 10)
if m < n and m % 10 < 9: solve(m + 1)
solve(1)
return result
解法II 迭代(Iterative)构造法
该解法实际上是解法I的迭代形式,可以类比二叉树先根遍历的迭代算法,需要用到栈(Stack)数据结构。
Python代码:
class Solution(object):
def lexicalOrder(self, n):
"""
:type n: int
:rtype: List[int]
"""
result = []
stack = [1]
while stack:
y = stack.pop()
result.append(y)
if y < n and y % 10 < 9:
stack.append(y + 1)
if y * 10 <= n:
stack.append(y * 10)
return result
下面的代码是迭代算法的另一种实现形式。
Python代码:
class Solution(object):
def lexicalOrder(self, n):
"""
:type n: int
:rtype: List[int]
"""
result = []
stack = []
x = 1
while x <= n:
stack.append(x)
result.append(x)
x *= 10
while stack:
y = stack.pop()
if y % 10 == 9: continue
y += 1
while y <= n:
stack.append(y)
result.append(y)
y *= 10
return result
本文链接:http://bookshadow.com/weblog/2016/08/21/leetcode-lexicographical-numbers/
请尊重作者的劳动成果,转载请注明出处!书影博客保留对文章的所有权利。