2020暑期實習後臺開發字節跳動筆試

1

輸入:第一行爲操作總數Q,之後有Q行。每行一個操作。
操作1,將字符串加在原字符串末尾。
操作2,給定長度,從字符串末尾刪除。
操作3,查詢現在字符串中第k個字符。
操作4,回滾一次操作(只回滾增刪操作)。
難度:easy
耗時:10min

public class Main {
    static StringBuilder sb = new StringBuilder();
    static Stack<String> st = new Stack();
    
    private static void add(String s) {
        st.push(sb.toString());
        sb.append(s);
    }
    
    private static char search(int pos) {
        return sb.charAt(pos-1);
    }
    
    private static void delete(int len) {
        st.push(sb.toString());
        sb.setLength(sb.length() - len);
    }
    
    private static void rollback() {
        sb = new StringBuilder(st.pop());
    }
    
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int Q = sc.nextInt();
        sc.nextLine();
        for (int j = 0; j < Q; j++) {
            String[] arr = sc.nextLine().split("\\s+");
            if (arr[0].equals("1"))
                add(arr[1]);
            else if (arr[0].equals("2"))
                delete(Integer.parseInt(arr[1]));
            else if (arr[0].equals("3")) {
                char c = search(Integer.parseInt(arr[1]));
                System.out.println(c);
            } else
                rollback();
        }
    }
}

2

輸入:第一行爲需要翻譯的文本M。len(M) <= 50000.
第二行爲字典中單詞數n。2 <= n <= 50000.
每一個單詞長度不超過20。
之後有n行,每一行代表一個單詞。
返回總共有多少種翻譯文本的方式。
返回的結果需要%835672545。
樣例:

abcba
5
a
ab
ba
bc
cb

// 輸出2
ab | cb | a
a | bc | ba

難度:medium
耗時:50min
一開始沒有降維,MLE。

public class Main {
    static final int kMod = 835672545;
    private static int search(HashSet<String> dict, String s) {
        int n = s.length();
        int[][] dp = new int[n+1][n+1];
        for (int i = 1; i <= n; i++)
            for (int j = i; j <= n; j++) {
                String tmp = s.substring(i-1, j);
                if (dict.contains(tmp))
                    dp[i][j] = 1;
            }
        for (int len = 1; len <= n; len++) {
            for (int i = 1; i+len-1 <= n; i++) {
                int j = i + len - 1;
                for (int k = i; k < j; k++) {
                    String s2 = s.substring(k, j);
                    if (dp[i][k] > 0 && dict.contains(s2)) {
                        dp[i][j] = (dp[i][j] + dp[i][k]) % kMod; 
                    }
                }
            }
        }
//        System.out.println(dp[1][1]); //a
//        System.out.println(dp[1][2]); // ab
//        System.out.println(dp[1][3]); // a | bc
//        System.out.println(dp[1][4]); // ab | cb
        return dp[1][n];
    }
    
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String target = sc.nextLine();
        int Q = sc.nextInt();
        sc.nextLine();
        HashSet<String> dict = new HashSet();
        for (int j = 0; j < Q; j++) {
            dict.add(sc.nextLine());
        }
        System.out.println(search(dict, target));
    }

}

第二次,沒有用Math.max優化長度,TLE。而且顯示test case通過率爲0,特別慌。
第三次終於AC。

public class Main {
    static final int kMod = 835672545;
    private static int search(HashSet<String> dict, String s) {
        int n = s.length();
        int[] dp = new int[n+1];
        dp[0] = 1;
        for (int r = 1; r <= n; r++) {
            for (int l = Math.max(1, r-20); l <= r; l++) {
                String tmp = s.substring(l-1, r);
                if (dp[l-1] > 0 && dict.contains(tmp))
                    dp[r] = (dp[r] + dp[l-1]) % kMod; 
            }
        }

        return dp[n];
    }
    
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String target = sc.nextLine();
        int Q = sc.nextInt();
        sc.nextLine();
        HashSet<String> dict = new HashSet();
        for (int j = 0; j < Q; j++) {
            dict.add(sc.nextLine());
        }
        System.out.println(search(dict, target));
    }
}

3

輸入:第一行兩個整形,m表示天數,n表示襪子數量(只)。
第二行是每隻襪子的顏色(用整形表示)。
之後有m行,每一天穿兩隻固定序號的襪子。但是必須保證兩隻襪子顏色一樣。如果不一樣,需要塗改襪子的顏色使這兩隻襪子的顏色能夠匹配。代價爲1。
返回最小代價。
難度:medium - hard
耗時:10min
應該是個dp問題。但是我連暴力解都沒寫出來。下面是個錯誤解法。

public class Main {
    static int[] color;
    static int[] color2;
    static int[][] comb;
    static int m;// number of days
    static int n;// number of socks
    private static int paint() {
        // dp[i][j][k] := min number of painting
        // in day i, painting j-th sock to color k
//        int[][][] dp = new int[m+1][n][n];
//        dp[0] = color.clone();
        int cnt = 0;
        for (int i = 0; i < m; i++) {
            int sock1 = comb[i][0];
            int sock2 = comb[i][1];
            boolean same1 = true;
            boolean same2 = true;
            if (color[sock1] != color[sock2]) {
                color[sock1] = color[sock2];
                same1 = false;
            }
            if (color2[sock1] != color2[sock2]) {
                color2[sock2] = color2[sock1];
                same2 = false;
            }
            if (!same1 && !same2)
                cnt++;
        }
        return cnt;
    }

    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        n = sc.nextInt();  
        m = sc.nextInt();  
        color = new int[n+1];
        comb = new int[m][2];
        for (int i = 1; i <= n; i++) {
            int c = sc.nextInt();
            color[i] = c;
        }
        color2 = color.clone();
        sc.nextLine();
        for (int j = 0; j < m; j++) {
            String[] arr = sc.nextLine().split("\\s");
            comb[j][0] = Integer.parseInt(arr[0]);
            comb[j][1] = Integer.parseInt(arr[1]);
        }
        System.out.println(paint());
    }
}

4

對給定字符串有兩種操作。
操作1,修改第k個字符爲新字符c。
操作2,查詢給定範圍內不同字符的個數。
難度:hard
耗時:10min
沒寫出來,只寫了一個暴力解,60%測試用例超時。
我估計使用Trie。

public class Main {
    static StringBuilder sb = null;

    private static int query(int l, int r) {
        HashSet<Character> cnt = new HashSet();
        for (int i = l-1; i < r; i++) {
            cnt.add(sb.charAt(i));
        }
        return cnt.size();
    }

    private static void update(int pos, String s) {
        sb.setCharAt(pos-1, s.charAt(0));
    }

    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String target = sc.nextLine();
        sb = new StringBuilder(target);
        int Q = sc.nextInt();
        sc.nextLine();
        HashSet<String> dict = new HashSet();
        for (int j = 0; j < Q; j++) {
            String[] arr = sc.nextLine().split("\\s");
            if (arr[0].equals("2")) { // query
                System.out.println(query(Integer.parseInt(arr[1]), Integer.parseInt(arr[2])));
            } else {
                update(Integer.parseInt(arr[1]), arr[2]);
            }
        }
    }
}

做完心態是崩潰的。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章