Problem:
Score : 300 points

Problem Statement

You are given an integer N. Among the integers between 1 and N (inclusive), how many Shichi-Go-San numbers (literally "Seven-Five-Three numbers") are there?

Here, a Shichi-Go-San number is a positive integer that satisfies the following condition:

When the number is written in base ten, each of the digits 7, 5 and 3 appears at least once, and the other digits never appear.

Constraints

1 \leq N < 10^9

N is an integer.

Input

Input is given from Standard Input in the following format:

N

Output

Print the number of the Shichi-Go-San numbers between 1 and N (inclusive).

Sample Input 1

575

Sample Output 1

4

There are four Shichi-Go-San numbers not greater than 575: 357, 375, 537 and 573.

Sample Input 2

3600

Sample Output 2

13

There are 13 Shichi-Go-San numbers not greater than 3600: the above four numbers, 735, 753, 3357, 3375, 3537, 3557, 3573, 3575 and 3577.

Sample Input 3

999999999

Sample Output 3

26484

Solution in Kotlin (1.0.0) (judge verdict: Accepted)

import java.io.IOException
import java.io.InputStream
import java.lang.Math.abs
import java.util.*
import java.util.Collections.sort
import java.util.Collections.swap

fun main(args: Array<String>) {
    val sc = Scanner(System.`in`)
    val n = sc.nextInt()
    val digit = n.toString().length
    var ans = 0
    for (s in 0..digit - 3) for (f in 0..digit - 3) for (t in 0..digit - 3) {
        if (s + f + t + 3 > digit) continue
        val list = mutableListOf(7, 5, 3)
        list.addAll(Array(s) { 7 })
        list.addAll(Array(f) { 5 })
        list.addAll(Array(t) { 3 })
        list.sort()
        do {
            if (list.joinToString("").toInt() <= n) ans++
            else break
        } while (nextPermutation(list))
    }
    println(ans)
}

fun <T : Comparable<T>> nextPermutation(list: List<T>): Boolean {
    val size = list.size
    for (i in size - 1 downTo 1) {
        if (list[i - 1] < list[i]) {
            val t = list[i - 1]
            var ok = i
            var ng = size
            while (abs(ok - ng) > 1) {
                val mid = (ok + ng) / 2
                if (list[mid] > t) ok = mid
                else ng = mid
            }
            swap(list, i - 1, ok)
            sort(list.subList(i, size))
            return true
        }
    }
    return false
}

class Scanner(private val `in`: InputStream) {
    private val buffer = ByteArray(1024)
    private var ptr = 0
    private var buflen = 0

    private fun hasNextByte(): Boolean {
        if (ptr < buflen) return true
        else {
            ptr = 0
            try {
                buflen = `in`.read(buffer)
            } catch (e: IOException) {
                e.printStackTrace()
            }
            if (buflen <= 0) return false
        }
        return true
    }

    private fun readByte(): Byte = if (hasNextByte()) buffer[ptr++] else -1

    private fun isPrintableChar(c: Char): Boolean = c in '!'..'~'

    private fun skipUnprintable() {
        while (hasNextByte() && !isPrintableChar(buffer[ptr].toChar())) ptr++
    }

    fun hasNext(): Boolean {
        skipUnprintable()
        return hasNextByte()
    }

    fun next(): String {
        if (!hasNext()) throw NoSuchElementException()
        val sb = StringBuilder()
        var b = readByte()
        while (isPrintableChar(b.toChar())) {
            sb.appendCodePoint(b.toInt())
            b = readByte()
        }
        return sb.toString()
    }

    fun nextInt(): Int {
        if (!hasNext()) throw NoSuchElementException()
        var n = 0
        var minus = false
        var b = readByte()
        if (b.toChar() == '-') {
            minus = true
            b = readByte()
        }
        if (b.toChar() !in '0'..'9') throw NumberFormatException()
        while (true) {
            if (b.toChar() in '0'..'9') {
                n *= 10
                n += b - '0'.toByte()
            } else return if (b.toInt() == -1 || !isPrintableChar(b.toChar())) {
                if (minus) -n else n
            } else {
                throw NumberFormatException()
            }
            b = readByte()
        }
    }

    fun nextInts(n: Int): Array<Int> = Array(n) { nextInt() }

    fun nextIntArray(n: Int): IntArray = IntArray(n) { nextInt() }

    fun nextIntArrays(n: Int, m: Int): Array<IntArray> {
        val arrays = Array(m) { IntArray(n) }
        for (i in 0 until n) {
            for (j in 0 until m) {
                arrays[j][i] = nextInt()
            }
        }
        return arrays
    }

    fun nextLong(): Long {
        if (!hasNext()) throw NoSuchElementException()
        var n: Long = 0
        var minus = false
        var b = readByte()
        if (b == '-'.toByte()) {
            minus = true
            b = readByte()
        }
        if (b.toChar() !in '0'..'9') throw NumberFormatException()
        while (true) {
            if (b.toChar() in '0'..'9') {
                n *= 10
                n += (b - '0'.toByte()).toLong()
            } else return if (b.toInt() == -1 || !isPrintableChar(b.toChar())) {
                if (minus) -n else n
            } else {
                throw NumberFormatException()
            }
            b = readByte()
        }
    }

    fun nextLongs(n: Int): Array<Long> = Array(n) { nextLong() }

    fun nextLongArray(n: Int): LongArray = LongArray(n) { nextLong() }

    fun nextLongArrays(n: Int, m: Int): Array<LongArray> {
        val arrays = Array(m) { LongArray(n) }
        for (i in 0 until n) {
            for (j in 0 until m) {
                arrays[j][i] = nextLong()
            }
        }
        return arrays
    }
}