E卷-出租车计费(100分)

出租车计费

问题描述

K小姐打了一辆出租车去上班。出于职业敏感,她注意到这辆出租车的计费表有点问题,总是偏大。出租车司机解释说他不喜欢数字4,所以改装了计费表,任何数字位置遇到数字4就直接跳过,其余功能都正常。比如:

  1. 再多 元就变为
  2. 再多 元变为
  3. 再多 元变为

K小姐识破了司机的伎俩,准备利用自己的学识打败司机的阴谋。

给出计费表的表面读数,返回实际产生的费用。

输入格式

只有一行,数字 ,表示里程表的读数。

输出格式

一个数字,表示实际产生的费用。以回车结束。

样例输入

5

样例输出

4

样例解释

表示计费表的表面读数, 表示实际产生的费用其实只有 元。

样例输入

17

样例输出

15

样例输入

100

样例输出

81

数据范围

题解

这道题目的本质是要理解并逆转计费表的计数规则。计费表跳过所有包含 4 的数字。

解题思路如下:

  1. 理解计数规则: 在这个特殊的计数系统中,每个位置实际上只有 9 个可能的数字(0-3, 5-9),而不是通常的 10 个。

  2. 逐位分析: 从最高位开始,逐位分析数字。对于每一位,我们需要:

    • 将当前结果乘以 9(因为每个位置只有 9 个可能的数字)
    • 加上当前位的数字
    • 如果当前位的数字大于 4,则减 1(因为 4 被跳过了)
  3. 累积结果: 重复上述步骤,直到处理完所有位。

参考代码

  • Python
# 读取输入
n = int(input())
digits = []

# 将数字分解为单个数字并存储
while n > 0:
    digits.append(n % 10)
    n //= 10

# 反转数字列表,使其从最高位到最低位
digits.reverse()
actual = 0

# 计算实际费用
for d in digits:
    actual = actual * 9 + d
    if d > 4:
        actual -= 1

# 输出结果
print(actual)
  • C
#include <stdio.h>
#include <stdlib.h>

int main() {
    int n, i, len = 0;
    int digits[10];  // 假设输入不超过10位数
    int actual = 0;

    // 读取输入
    scanf("%d", &n);

    // 将数字分解为单个数字并存储
    while (n > 0) {
        digits[len++] = n % 10;
        n /= 10;
    }

    // 从最高位到最低位计算实际费用
    for (i = len - 1; i >= 0; i--) {
        actual = actual * 9 + digits[i];
        if (digits[i] > 4) {
            actual -= 1;
        }
    }

    // 输出结果
    printf("%d\n", actual);

    return 0;
}
  • Javascript
const readline = require('readline');

const rl = readline.createInterface({
    input: process.stdin,
    output: process.stdout
});

rl.question('', (input) => {
    let n = parseInt(input);
    let digits = [];

    // 将数字分解为单个数字并存储
    while (n > 0) {
        digits.push(n % 10);
        n = Math.floor(n / 10);
    }

    // 反转数字数组,使其从最高位到最低位
    digits.reverse();
    let actual = 0;

    // 计算实际费用
    for (let d of digits) {
        actual = actual * 9 + d;
        if (d > 4) {
            actual -= 1;
        }
    }

    // 输出结果
    console.log(actual);
    rl.close();
});
  • Java
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        List<Integer> digits = new ArrayList<>();

        // 将数字分解为单个数字并存储
        while (n > 0) {
            digits.add(n % 10);
            n /= 10;
        }

        // 反转数字列表,使其从最高位到最低位
        Collections.reverse(digits);
        int actual = 0;

        // 计算实际费用
        for (int d : digits) {
            actual = actual * 9 + d;
            if (d > 4) {
                actual -= 1;
            }
        }

        // 输出结果
        System.out.println(actual);
        scanner.close();
    }
}
  • Cpp
#include <iostream>
#include <vector>
#include <algorithm>

using namespace std;

int main() {
    int n;
    vector<int> digits;

    // 读取输入
    cin >> n;

    // 将数字分解为单个数字并存储
    while (n > 0) {
        digits.push_back(n % 10);
        n /= 10;
    }

    // 反转数字向量,使其从最高位到最低位
    reverse(digits.begin(), digits.end());
    int actual = 0;

    // 计算实际费用
    for (int d : digits) {
        actual = actual * 9 + d;
        if (d > 4) {
            actual -= 1;
        }
    }

    // 输出结果
    cout << actual << endl;

    return 0;
}
#OD#
OD刷题笔记 文章被收录于专栏

本专栏收集并整理了一些刷题笔记

全部评论

相关推荐

1 1 评论
分享
牛客网
牛客企业服务