1. 程式人生 > 其它 >【Lintcode】1267. Lexicographical Numbers

【Lintcode】1267. Lexicographical Numbers

技術標籤:# DFS、BFS與圖論leetcode演算法dfs

題目地址:

https://www.lintcode.com/problem/lexicographical-numbers/description

給定一個正整數 n n n,返回 1 ∼ n 1\sim n 1n的所有數,按字典序排序。

思路是DFS。DFS天生適合字典序。遞迴第一層是從 1 ∼ 9 1\sim 9 19遍歷,每遍歷到一個數就進入下一層遞迴,第二層從 0 ∼ 9 0\sim 9 09,接在第一層的數後面。例如第一層遍歷到 1 1 1,如果 n < 100 n<100 n<100,進入第二層的時候得到 10 , 11 , 12 , . . . 10,11,12,...

10,11,12,...恰好是字典序緊接著的後面的若干數;如果 n ≥ 100 n\ge 100 n100,則遍歷到 10 10 10的時候又要進入下一層遞迴,得到 100 , 101 , . . . 100,101,... 100,101,...。如果遍歷到大於 n n n的數的時候就返回上一層遞迴。遞迴的順序訪問的數就是字典序。但是要注意 0 0 0不要加入答案裡。程式碼如下:

import java.util.ArrayList;
import java.util.List;

public class Solution {
    /**
     * @param n: an integer
     * @return: 1 - n in lexicographical order
     */
public List<Integer> lexicalOrder(int n) { // write your code here List<Integer> res = new ArrayList<>(); dfs(0, n, true, res); return res; } private void dfs(int cur, int n, boolean start, List<Integer> res) { // 大於n了就返回上一層遞迴
if (cur > n) { return; } // 0要排除掉 if (cur != 0) { res.add(cur); } // 如果是遞迴第一層,則從1開始迴圈,否則從0開始 for (int i = start ? 1 : 0; i <= 9; i++) { dfs(cur * 10 + i, n, false, res); } } }

時間複雜度 O ( n ) O(n) O(n),空間 O ( log ⁡ n ) O(\log n) O(logn)