Problem:
F: ごちうさ数

問題

ごちうさが大好きなAORイカちゃんは「ごちうさ数」を定義した。
ごちうさ数とは、 $10$ 進表記において「 $51?3$ 」を含む自然数のことである。

$?$ は $0$ 〜 $9$ のどの数字であってもよい。

$N$ 以下の自然数のうち、ごちうさ数の個数を求めよ。

制約

$1 \le N < 10^{18}$

入力

$N$

出力

ごちうさ数の個数を一行で出力せよ。また末尾に改行を出力せよ。

サンプル

サンプル入力 1

5124

サンプル出力 1

3

$5124$ 以下のごちうさ数は、$5103$ , $5113$ , $5123$ の 三つである。

サンプル入力 2

60000

サンプル出力 2

160

サンプル入力 3

100000

サンプル出力 3

200

Solution in JAVA (judge verdict: Accepted)

import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        char[] numArr = sc.next().toCharArray();
        int length = numArr.length;
        int[] arr = new int[length];
        for (int i = 0; i < length; i++) {
            arr[i] = numArr[i] - '0';
        }
        long[][][][][][] dp = new long[length + 1][10][10][10][10][2];
        dp[0][0][0][0][0][1] = 1;
        long[][] counts = new long[length + 1][2];
        for (int i = 1; i <= length; i++) {
            for (int a = 0; a < 10; a++) {
                for (int b = 0; b < 10; b++) {
                    for (int c = 0; c < 10; c++) {
                        for (int d = 0; d < 10; d++) {
                            for (int e = 0; e < 10; e++) {
                                dp[i][b][c][d][e][0] += dp[i - 1][a][b][c][d][0];
                                if (e < arr[i - 1]) {
                                    dp[i][b][c][d][e][0] += dp[i - 1][a][b][c][d][1];
                                } else if (e == arr[i - 1]) {
                                    dp[i][b][c][d][e][1] += dp[i - 1][a][b][c][d][1];
                                }
                            }
                        }
                    }
                }
            }
            for (int e = 0; e < 10; e++) {
                counts[i][0] += counts[i - 1][0];
                if (e < arr[i - 1]) {
                    counts[i][0] += counts[i - 1][1];
                } else if (e == arr[i- 1]) {
                    counts[i][1] += counts[i - 1][1];
                }
            }
            for (int j = 0; j < 10; j++) {
                counts[i][0] += dp[i][5][1][j][3][0];
                counts[i][1] += dp[i][5][1][j][3][1];
                dp[i][5][1][j][3][0] = 0;
                dp[i][5][1][j][3][1] = 0;
            }
        }
        System.out.println(counts[length][0] + counts[length][1]);
    }
}